【刷题之路】最小的K个数

原创 2016年07月29日 17:59:48

输入n个整数,找出其中最小的K个数。例如输入4,5,1,6,2,7,3,8这8个数字,则最小的4个数字是1,2,3,4。

最优方法可以做到n*log(k)。做法就是使用堆排序,只维护一个规模为k的大根堆,之后遍历所有的数字,一旦后面数字比堆顶小,则交换两数,并重新调整大根堆,遍历完成后堆中元素就是最小的k个数(但是这K个数不一定是排序的)

代码如下:

class Solution {
public:
    vector<int> GetLeastNumbers_Solution(vector<int> input, int k){
        int i,j=0;
        vector<int> res;
        int n=input.size();
        if(n<k) return res; //如果K比总数还大,直接返回
        maxheap(input,k); //由前K个数建立一个大根堆
        for(i=k;i<n;i++){
            if(input[0]>input[i]) swap(input[0],input[i]);  //之后的数字只要比堆顶大,则改变堆顶,并调整K规模的大根堆
            fixdown(input,0,k);
        }
        for(i=0;i<k;i++) res.push_back(input[i]); //遍历完成后,输出前K个即为最小的K个数
        return res;
        
    }
    void maxheap(vector<int> &num,int n){
        int i;
        for(i=n/2-1;i>=0;i--){
            fixdown(num,i,n-1);
        }
    }
    void fixdown(vector<int> &num, int i,int n){ //这里的n是下标,所以之前的fixdown要是n-1
        int j;
        int flag=1;
        while(2*i+1<n && flag){  //常规堆排序做法,不详述
            if(2*i+2>=n) j=2*i+1;
            else{
                if(num[2*i+2]<num[2*i+1]) j=2*i+1;
                else j=2*i+2;
            }
            if(num[i]<num[j]){
                swap(num[i],num[j]);
                i=j;
            }
            else flag=0;
        }
    }
};

版权声明:本文为博主原创文章,未经博主允许不得转载。

百度2016实习 前端试题中的编程题1:输出乘法表中第k小的数的值

百度2016实习 前端试题中的编程题1 输出乘法表中倒数第k大的数 题目大意: n*m的一个乘法表,进行非递减排序后,输出第k个数  (1 ≤ n, m ≤ 5·10^5; 1 ≤ k ≤ n·...
  • yanglr2010
  • yanglr2010
  • 2016年04月22日 16:01
  • 1320

Python 刷题(想练python的可以对着刷一刷,持续更新)

这道题的意思是说
  • geniusluzh
  • geniusluzh
  • 2014年04月23日 10:36
  • 7731

leetcode刷题经验

语言不是最重要的,思想最重要从做上面的题,我发现我更擅长一些数学技巧不高的程序题,习惯靠直觉立马书写代码,而非严格推理之后,再书写代码对于链表的题比较擅长,链表可以在纸上画画,关键要考虑的问题,就是链...
  • basycia
  • basycia
  • 2016年02月28日 15:31
  • 1392

谈谈程序员面试之刷题

前一段时间有一个非常有趣的故事(http://www.pingwest.com/sorry-cant-hire-you/  ),Max Howell (Homebrew的作者) 在 Google 面试...
  • github_39335046
  • github_39335046
  • 2017年06月29日 17:03
  • 1740

LeetCode刷题指南(一)

以下是我个人做题过程中的一些体会: 1. LeetCode的题库越来越大,截止到目前,已经有321个问题了。对于大多数人来说,没有时间也没有必要把所有题目都做一遍(时间充裕可以随意)。刷个100题左...
  • Lnho2015
  • Lnho2015
  • 2016年03月23日 15:02
  • 38299

比较好的刷题网站推荐

http://www.cnblogs.com/DarrenChan/p/5648422.html 1.Leetcode鼎鼎大名的Leetcode,据不完全统计在上面被刷过的题可以围绕地球...
  • dipolar
  • dipolar
  • 2017年03月09日 11:56
  • 750

bzoj刷题(shui)记录

放假刷了一个月的水题,集中写一下题解吧。bzoj1858:线段树随便维护一下。 code bzoj2705:莫比乌斯反演裸题。 code bzoj1202:并查集,但是我写了一种跟floyd很像的...
  • FZHvampire
  • FZHvampire
  • 2015年08月31日 11:26
  • 1655

手把手教你用C++ 写ACM自动刷题神器(冲入HDU首页)

少年,作为苦练ACM,通宵刷题的你 是不是想着有一天能够荣登各大OJ榜首,俯瞰芸芸众生,唔....要做到这件事情可是需要一定天赋的哦! 博主本身也搞过一段时间的acm,对刷题深有感触,不信可以去看我...
  • qq_28954601
  • qq_28954601
  • 2016年04月24日 10:12
  • 2128

topcoder 刷题笔录 初级篇(一)

摘要:本系列文章为在topcoder上的刷题记录和心得,计划刷题500道。其中,初级题目30道,撰文三篇;中级题目60道,撰文六篇;其他高级题目100道,撰文10篇。 1.题目1——SRM146 ...
  • trochiluses
  • trochiluses
  • 2013年12月20日 16:00
  • 2554

一、简单刷题APP(题库是Excel)之项目功能和效果图

这是本人的第一篇博客,自己也是菜鸟,如有不妥之处,欢迎指教,谢谢了。只是想借此机会自己也整理一下笔记。 在此想感谢各位牛人还有这个平台,我在学习和做项目的过程中遇到了很多问题,CSDN博客大都能解决...
  • qq_35638837
  • qq_35638837
  • 2017年04月03日 14:16
  • 699
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:【刷题之路】最小的K个数
举报原因:
原因补充:

(最多只允许输入30个字)