排序算法的稳定性
相同的值,会不会因为某种排序算法,相对次序被打乱,如果不会被打乱,这个排序具有稳定性,如果会被打乱,则不具备稳定性。
- 冒泡排序可以做到稳定的,相等,不交换即可,让下一个相同值往下沉。
- 插入排序也可以做到稳定的。相等,不交换即可,不会跑到前面以及出现的值的前面去。
- 选择排序做不到稳定。肯定要交换的。
- 归并排序可以做到稳定,归并时,左边右边相等,先拷贝左边即可。
- 快速排序不能做到稳定性。
- 堆排序不能做到稳定性。
稳定性的意义:业务往往需要稳定性。分数排序后,再班级排序,则每个班都会按照分数进行排序。
希望原始信息不要被抹去,排序后还能留下来,则需要有稳定性。
工程中的综合排序算法
工程中的综合排序算法,数组长度小于60,直接用插入排序(样本量比较大,分治(r-l)小于60,则直接插排,原因常数项低,O(N2)的劣势不明显),基础类型,则直接使用快排,相同值无差异,所以可以选用无稳定性的快排,如果是自己写的类,相同的对象具有前后顺序差异,则根据比较器,使用归并排序,具有稳定性。
有关排序问题的补充:
01 stable sort,01标准问题,奇偶,大于,小于等于,都是01标准,是否存在分离,同时还不改变相对次序,额外空间复杂度O(1),时间复杂度O(N)。实际上不存在,做不到,因为快排不具有稳定性。荷兰国旗也做不到稳定性。
比较器
返回负数,则第一个参数放前面,正数,第二个参数放前面,0,则认为相等。
c++:重载比较运算符
可用在优先队列(堆),
比较好用的有序结构,都会提供比较器构造。只要定义好两个对象怎么比即可。lambda表达式。,就可以拓展到现实世界中的很多东西。
红黑树,对应c++map,set,有序集合。
更多排序算法
实际中用的不多,和数据状况有关,不是基于比较的排序。
桶排序
时间复杂度O(N),不基于比较,基于桶,一种数据状况出现的次数,容器。可以是数组中的一个位置,也可能是一个队列,一个链表。每一个东西扔到各自归属的桶里面。
桶排序就是一个大的概念,计数排序是里面的一个具体的实例。还有一种基数排序。
数据量大的话,额外空间就会消耗很大,跟数据状况详细相关。
**借用桶的概念,但是没有进行桶排序。**方法很好!
每个桶记录min,max,还有个bool表示有没有数进桶,依次将该桶的最小值和上一个非空桶的最大值做差值,一定有一个答案。
设计空桶目的:为了否定来自一个桶内部的可能性。但不代表最大差值就在空桶两侧。
确定在几号桶