面试题30:最小的k个数
来源:互联网 发布:mac 相对于卷宗的格式 编辑:程序博客网 时间:2024/06/03 07:53
1.输入n个整数,找出其中的最小的k个数,例如输入4,5,1,6,2,7,3,8 这8个数字,则其中最小的4个数字是1,2,3,4,。
分析:
方法一,可以采用类似快速排序的解法,基于数组中第k个数来进行调整,使得比第k个数字大的所有数字都在数组的右边,小的都在第k个数字的左边。
方法二:可以创建一个大小为k的容器来存储最小的k个数,如果容器中的书少于k个,则直接把读入的整数放入容器中,如果容器满了,此时得找出这k个数中的最大值,再拿这次待插入的值和最大值进行比较,如果比它大,则不进行插入,如果比它小,则替换k个数中的最大值,直到数组中的所有数访问完,则最后容器中的数就是k个最小的数。应为当容器满的时候,每次得计算容器中的最大值,为了在短时间内计算出最大值,可以采用类似红黑树的结构,假设k个节点,则可以在lg(k)的时间内找出最大值。
源码:
/*** 功能说明:Description* 作者:K0713* 日期:2016-7-22**/#include<iostream>#include<vector>#include<set>using namespace std;typedef multiset<int, greater<int> > intSet;typedef multiset<int, greater<int> >::iterator setIterator;//产生随机数int RandomInRange(int min, int max);//交换两个数值void Swap(int* num1, int* num2);//基于快速排序的划分int Partition(int data[], int length, int start, int end);//基于快速排序的解法void GetLeastNumbers_Solution1(int* input, int n, int* output, int k);//基于替换的解法void GetLeastNumbers_Solution2(const vector<int>& data, intSet& leastNumbers, int k);int main(){int data[] = {4, 5, 1, 6, 2, 7, 3, 8};vector<int> vectorData;for(int i = 0; i < 8; ++ i)vectorData.push_back(data[i]);int k=4;int* output = new int[k];cout<<"solution 1: "<<endl;GetLeastNumbers_Solution1(data, 8, output, k);for(int i = 0; i < k; ++ i)cout<<output[i]<<" ";cout<<endl;cout<<"solution 2: "<<endl;intSet leastNumbers;GetLeastNumbers_Solution2(vectorData, leastNumbers, k);for(setIterator iter = leastNumbers.begin(); iter != leastNumbers.end(); ++iter)cout<< *iter<<" ";cout<<endl;system("PAUSE");return 0;}int Partition(int data[], int length, int start, int end){if (data == NULL || length <= 0 || start < 0 || end >= length)throw new std::exception("Invalid Parameters");int index = RandomInRange(start, end);Swap(&data[index], &data[end]);int small = start - 1;for (index = start; index < end; ++index){if (data[index] < data[end]){++small;if (small != index)Swap(&data[index], &data[small]);}}++small;Swap(&data[small], &data[end]);return small;}int RandomInRange(int min, int max){int random = rand() % (max - min + 1) + min;return random;}void Swap(int* num1, int* num2){int temp = *num1;*num1 = *num2;*num2 = temp;}void GetLeastNumbers_Solution1(int* input, int n, int* output, int k){if(input == NULL || output == NULL || k > n || n <= 0 || k <= 0)return;int start = 0;int end = n - 1;int index = Partition(input, n, start, end);while(index != k - 1){if(index > k - 1){end = index - 1;index = Partition(input, n, start, end);}else{start = index + 1;index = Partition(input, n, start, end);}}for(int i = 0; i < k; ++i)output[i] = input[i];}void GetLeastNumbers_Solution2(const vector<int>& data, intSet& leastNumbers, int k){leastNumbers.clear();if(k < 1 || data.size() < k)return;vector<int>::const_iterator iter = data.begin();for(; iter != data.end(); ++ iter){if((leastNumbers.size()) < k)leastNumbers.insert(*iter);else{setIterator iterGreatest = leastNumbers.begin();if(*iter < *(leastNumbers.begin())){leastNumbers.erase(iterGreatest);leastNumbers.insert(*iter);}}}}
0 0
- 面试题30:最小的k个数
- 面试题30 最小的K个数
- 面试题30:最小的K个数
- 面试题30 最小的K个数
- 面试题30:最小的K个数
- 面试题30:最小的k个数
- 面试题30:最小的K个数
- 面试题30:最小的k个数
- 面试题30最小的k个数
- 面试题30:最小的k个数
- 面试题30:最小的k个数
- 面试题 30 : 最小的K个数
- 面试题26:最小的k个数
- 面试题:求最小的K个数。
- 面试题34:最小的K个数
- 面试题30.最小的K个数
- 剑指offer面试题30最小的k个数
- [剑指offer][面试题30]最小的k个数
- linux下ioctl()函数使用的详细说明
- PHP常量详解:define和const的区别
- C++中一个空类含有哪些默认的成员函数
- 较长输入行折成多行
- HDU-1700 Points on Cycle
- 面试题30:最小的k个数
- java算法之身份证号码验证
- 1479 小Y的数论题
- 起航
- javaScript笔记(九) 变量、作用域及内存
- java学习之路 之 高级类特性1-面向对象特征之三:多态
- C# 扩展方法
- java操作连接mysql
- CSS实现圆角,三角,五角星,五边形,爱心,12角星,8角星,圆,椭圆,圆圈,八卦