以前面试时被问一个问题:有10万个乱序的数,要前5个最大(或最小)的数?
作为一个没好好学算法的人,还没有算法时间、空间复杂度的概念,只提出了冒泡、快速排序等,然后取前5。这显然不是合理的做法。

读了几本书,有一点点心得,下面介绍两个做法:
假设:输入为[31,5,12,24,41,63,7,61,42,21,9,123,24...] ,总数为N=100000,要求前M=5个最大的数

  1. 对10万个建立二叉堆,然后应用堆排序5次,即取出前5个最大(或最小)的数。
    只是一个可行的方法,在此不敖述,具体可参见《数据结构与算法分析:C语言描述》、《数据结构(C语言版)》严蔚敏等书中的堆排序。

  2. 考虑:能否维护一个数据结构用来存储排好序的5个数,要求如果输入数大于5个中最小的数,就将其插入至正确位置,并删除最小的数。这样对输入进行一次遍历,即可找出最大的5个数。
    此处想到的是用单链表,首先对输入中前5个数字升序排序,插入空的链表中。

//简单冒泡排序,输入少,对整体性能影响可忽略不计
for(int j=1; j<M; j++){for(int k=0; k<M-j; k++){if(input[k]>input[k+1]){tmp = input[k];input[k] = input[k+1];input[k+1]=tmp;}}
}
for(int i=0; i<M; i++){Insert(input[i],L,P);//依次插入链表P = P->Next;
}

Position Tmp,TmpCell;
for( ; i<N; i++){ //对其余输入进行一次遍历P = Header(L); //表头do{Tmp = P;//暂存前驱元,保存位置P = P->Next;//第一个元素if( input[i] <= P->Value ){ //小于第一个元素或者后面的某一个元素if(P != L->Next){ //input[i]大小介于第一个元素与此位置的元素Insert(in[i],L1,Tmp); //插入TmpCell = L1->Next;L1->Next = TmpCell->Next;free( TmpCell ); //挤出第一个元素,也就是5+1=6个中最小的元素}break;}else if(input[i] > P->Value && IsLast( P, L )){ //如果大于最后一个(也就是最大的)元素Insert(in[i],L,P); //插入到最后TmpCell = L->Next; L->Next = TmpCell->Next; free(TmpCell); //删除第一个元素(6个中最小的)break;}} while( !IsLast(P, L) );
}

插入可能是这样的:

删除首元可能是这样的:

小结:当输入大数据量,而只需前m个最大(最小)值时,应用链表不失为一个好办法,它只对输入进行一次遍历,时间复杂度O(N),空间也只不过额外是一个含6个元素的链表大小而已。
欢迎指教。

堆排序\链表实现局部排序相关推荐

  1. 链表问题16——单链表的选择排序(python版本)

    题目 给定一个无序单链表头节点head,实现单链表的选择排序 要求:额外空间复杂度为O(1),时间复杂度O() 思路 选择排序是从未排序的部分中找到最小值,然后放在排好序部分的尾部. 开始整个链表都是 ...

  2. 链表问题16——单链表的选择排序

    题目 给定一个无序单链表头节点head,实现单链表的选择排序 要求:额外空间复杂度为O(1),时间复杂度O() 思路 选择排序是从未排序的部分中找到最小值,然后放在排好序部分的尾部. 开始整个链表都是 ...

  3. c语言单链表的字母排序,链表排序——选择排序法(纯C语言版)

    /********************************* 链表的排序 *******************************************/ /* =========== ...

  4. 两个有序单链表的合并排序算法

    设计两个有序单链表的合并排序算法 ListList MergeList(LiskList La, LinkList Lb){Lnode *pa = La->next;Lnode *pb = Lb ...

  5. SDUT_2121数据结构实验之链表六:有序链表的建立 (对建立的单项链表结构进行排序)

    点击打开链接 数据结构实验之链表六:有序链表的建立 Time Limit: 1000MS Memory Limit: 65536KB Submit Statistic Discuss Problem ...

  6. 处女座的签到题 (暴力+局部排序)

    题意: 平面上有n个点,问:平面上所有三角形面积第k大的三角形的面积是多少? 思路: 看到这个题我也是非常懵逼的,因为,我都是看别人的代码才写出来的 知识点1,三角形的面积已知三个点的坐标,求三角形面 ...

  7. C++实现对链表的选择排序算法(附完整源码)

    C++实现对链表的选择排序算法 C++实现对链表的选择排序算法完整源码(定义,实现,main函数测试) C++实现对链表的选择排序算法完整源码(定义,实现,main函数测试) #include < ...

  8. C++vector进行局部排序

    C++vector进行局部排序 话不多说了,直接上代码 #include<stdio.h>#include<iostream>#include<vector>#in ...

  9. 牛客题霸 单链表的选择排序 C++题解/答案

    牛客题霸 单链表的选择排序 C++题解/答案 题目描述 给定一个无序单链表,实现单链表的选择排序(按升序排序). 题解: 不可能手写排序,这辈子不可能手写排序.. 基础的链表操作,将链表内的数据存到v ...

最新文章

  1. armv8 汇编 绝对地址赋值_ARMv8带来的变化
  2. TCP/IP详解--第二十章
  3. 云计算平台中虚拟专用网和VPC有什么区别?
  4. Redis 的主从复制太强大了!
  5. linux的write是线程安全的吗,socket的write/send还是是否是线程安全?
  6. ABAP单元帮助类的两种使用方式
  7. android主要文件的作用是什么,androidmanifest.xml文件的作用是什么
  8. Centos 7编译安装 LAMP 环境
  9. 关于【CDQ分治】的学习
  10. 以后所有经济时事的点评都不在这里
  11. java发送网络图片邮件
  12. 软件工程(系统流程图讲解)
  13. 什么是偏振光和UV光?
  14. codeforces topcoder 指南
  15. 微信小程序的选择收货地址、新增地址、地址管理等模块的总结(1)
  16. 我不相信长夜将至,因为火把就在自己手中。
  17. wow登录服务器未响应,魔兽世界进不去 战网无法登陆和未响应怎么办
  18. 奥丁神叛虚拟机 台服登录不上游戏 账号无法登录游戏解决办法
  19. 除尘机器人毕业_一种除尘机器人的制作方法
  20. Excel格式刷使用

热门文章

  1. Android8.0适配那点事(二)
  2. Matlab设置Legend横排、分块
  3. JavaScript装逼指南
  4. 关于Animator获取当前剪辑长度
  5. corosync+pacemaker+crmsh配置高可用集群。
  6. scvmm2008R2创建委派管理员角色
  7. C#中Escape编码的加密、解密
  8. C#连接sqlserver数据库
  9. ACM Smallest Difference
  10. aspx后缀映射成html