[算法]在数组中找到出现次数大于N/K的数
题目:
1.给定一个整型数组,打印其中出现次数大于一半的数。如果没有出现这样的数,打印提示信息。
如:1,2,1输出1。 1,2,3输出no such number。
2.给定一个整型数组,再给一个整数K,打印所有出现次数大于N/K的数,如果没有这样的数,打印提示信息。
解答:
两道题都可以使用哈希表记录每个数出现的次数,额外的空间复杂度为O(N)。
其他的方法:
1.时间复杂度为O(N)。额外空间复杂度为O(1)。
public static void printHalfMajor(int[] arr) {
int cand = 0;
int times = 0;
for (int i = 0; i < arr.length; i++) {
if (times == 0) {
cand = arr[i];
times++;
} else if (arr[i] == cand) {
times++;
} else {
times--;
}
}
times = 0;
for (int i = 0; i < arr.length; i++) {
if (arr[i] == cand)
times++;
}
if (times > arr.length / 2) {
System.out.println(cand);
} else {
System.out.println("no such number.");
}
}
第一个for循环结束后,如果这样的数真的存在,那么cand的值就是所求的值。但是cand的值不一定就是所求的值。所以最后还要用for循环判断一下。
2.时间复杂度为O(N*K)。额外空间复杂度为O(K)。
public static void printKMajor(int[] arr, int K) {
if (K < 2) {
System.out.println("the value of K is invalid.");
return;
}
HashMap<Integer, Integer> cands = new HashMap<Integer, Integer>();
for (int i = 0; i != arr.length; i++) {
if (cands.containsKey(arr[i])) {
cands.put(arr[i], cands.get(arr[i]) + 1);
} else {
if (cands.size() == K - 1) {
allCandsMinusOne(cands);
} else {
cands.put(arr[i], 1);
}
}
}
HashMap<Integer, Integer> reals = getReals(arr, cands);
boolean hasPrint = false;
for (Entry<Integer, Integer> set : cands.entrySet()) {
Integer key = set.getKey();
if (reals.get(key) > arr.length / K) {
hasPrint = true;
System.out.print(key + " ");
}
}
System.out.println(hasPrint ? "" : "no such number.");
}
public static void allCandsMinusOne(HashMap<Integer, Integer> map) {
List<Integer> removeList = new LinkedList<Integer>();
for (Entry<Integer, Integer> set : map.entrySet()) {
Integer key = set.getKey();
Integer value = set.getValue();
if (value == 1) {
removeList.add(key);
}
map.put(key, value - 1);
}
for (Integer removeKey : removeList) {
map.remove(removeKey);
}
}
public static HashMap<Integer, Integer> getReals(int[] arr,
HashMap<Integer, Integer> cands) {
HashMap<Integer, Integer> reals = new HashMap<Integer, Integer>();
for (int i = 0; i != arr.length; i++) {
int curNum = arr[i];
if (cands.containsKey(curNum)) {
if (reals.containsKey(curNum)) {
reals.put(curNum, reals.get(curNum) + 1);
} else {
reals.put(curNum, 1);
}
}
}
return reals;
}
[算法]在数组中找到出现次数大于N/K的数的更多相关文章
- 《程序员代码面试指南》第八章 数组和矩阵问题 在数组中找到出现次数大于N/K 的数
题目 在数组中找到出现次数大于N/K 的数 java代码 package com.lizhouwei.chapter8; import java.util.ArrayList; import java ...
- 在数组中寻找出现次数大于N/K的数
给定一个int[]数组,给定一个整数k,打印所有出现次数大于N/k的数,没有的话,给出提示信息. === 核心思想:一次在数组中删除K个不同的数,不停的删除,直到剩下的数的种类不足K就停止删除,那么如 ...
- 算法总结之 在数组中找到出现次数 > N/K的数
题目1 给定一个整型数组arr, 打印其中出现次数大于一半的数, 如果没有这样的数,打印提示信息 进阶 给定一个整型数组arr, 再给定一个整数K, 打印所有出现次数大于 N/K的数,如果没有这样的 ...
- 剑指Offer面试题:32.数字在排序数组中出现的次数
一.题目:数字在排序数组中出现的次数 题目:统计一个数字在排序数组中出现的次数.例如输入排序数组{1,2,3,3,3,3,4,5}和数字3,由于3在这个数组中出现了4次,因此输出4. 二.解题思路 2 ...
- [LeetCode169]Majority Element求一个数组中出现次数大于n/2的数
题目: Given an array of size n, find the majority element. The majority element is the element that ap ...
- 编程算法 - 数字在排序数组中出现的次数 代码(C)
版权声明:本文为博主原创文章,未经博主同意不得转载. https://blog.csdn.net/u012515223/article/details/36869869 数字在排序数组中出现的次数 代 ...
- [PHP] 算法-统计一个数字在排序数组中出现的次数的PHP实现
统计一个数字在排序数组中出现的次数. 1.有序的数组查找,使用二分法 2.二分法查找第一次出现的位置,二分法查找最后一次出现的位置,end - start +1 left=getLeft(data,k ...
- 【剑指Offer】37、数字在排序数组中出现的次数
题目描述: 统计一个数字在排序数组中出现的次数.例如,输入排序数组{1,2,3,3,3,3,4,5}和数字3,由于数字3在该数组中出现了4次,所以函数返回4. 解题思路: 既然输入的数 ...
- 剑指Offer(三十七):数字在排序数组中出现的次数
剑指Offer(三十七):数字在排序数组中出现的次数 搜索微信公众号:'AI-ming3526'或者'计算机视觉这件小事' 获取更多算法.机器学习干货 csdn:https://blog.csdn.n ...
随机推荐
- Https单向认证和双向认证介绍
一.Http HyperText Transfer Protocol,超文本传输协议,是互联网上使用最广泛的一种协议,所有WWW文件必须遵循的标准.HTTP协议传输的数据都是未加密的,也就是明文的,因 ...
- shell 判断问题总结
#!/bin/bash #比如需要判断一个变量是否含有值: if [[ -z $1 ]] ; thenecho "Something like empty!"exit 0;fi # ...
- java之数字彩虹雨
© 版权声明:本文为博主原创文章,转载请注明出处 数字彩虹雨: 从上至下,随机出现一串字符串,以不同的速度运行到底部:类似于黑客帝国里面的场景 GitHub:https://github.com/Ta ...
- python函数形参中的*args和**kwargs
转载:https://www.cnblogs.com/xuyuanyuan123/p/6674645.html 多个实参,放到一个元组里面,以*开头,可以传多个参数:**是形参中按照关键字传值把多余的 ...
- win7-vs2012下安装.net frame work 的过程
第一, vs和.net的对应关系大致如下 vs2010----.net framework 4.0 vs2012----.net framework 4.5 vs2015----.net frame ...
- 50 years of Computer Architecture: From the Mainframe CPU to the Domain-Specific TPU and the Open RISC-V Instruction Set
1.1960年代(大型机) IBM发明了具有二进制兼容性的ISA——System/360,可以兼容一系列的8到64位的硬件产品,而不必更换操作系统.这是通过微编程实现的,每个计算机模型都有各自的ISA ...
- shell学习五十七天----linux任务管理,针对上一讲的总结和扩展
linux任务管理 在linux下有两类任务管理,各自是一次性和周期性.一次性是at和batch,周期性又分为系统不论什么和用户任务. 一次性任务: 1.命令格式:at [选项] time 2.选项: ...
- 《Lucene in Action》(第二版) 第一章节的学习总结 ---- 用最少的代码创建索引和搜索
第一章节是介绍性质,但是通过这一章节的学习,我理解到如下概念: 1.Lucene由两部分组成:索引和搜索.索引是通过对原始数据的解析,形成索引的过程:而搜索则是针对用户输入的查找要求,从索引中找到匹配 ...
- BlockingQueue的使用 http://www.cnblogs.com/liuling/p/2013-8-20-01.html
BlockingQueue的使用 本例介绍一个特殊的队列:BlockingQueue,如果BlockQueue 是空的,从BlockingQueue取东西的操作将会被阻断进入等待状态,直到Blocki ...
- kafka的并行度与JStorm性能优化
kafka的并行度与JStorm性能优化 > Consumers Messaging traditionally has two models: queuing and publish-subs ...