慎重选择排序算法

排序,在我们使用序列容器时经常使用。那如何进行排序呢。

对于排序,首先想到是sort和qsort,这两个首选sort,因为sort传入比较的函数对象,而qsort传入比较函数的指针,会多函数调用的过程。

但是sort也并非在任何场合下都完美。

1、sort不是稳定的排序,需要稳定的全排序则需要stable_sort。

2、有时候你并不需要一个全排序操作。比如你只需要对成绩等级最好的前10的学生做奖状,同时根据等级不同获取不同的奖学金,这时候全排序就显得浪费,而partial_sort的算法就刚刚好。

 如果只是给前10做同样的奖状,不分名次,那nth_element更合适,这个算法只找到最好的10个。

 这个函数nth_element与partial_sort不同的是,nth_element选出的前10个没有顺序。这两个函数对第一个和第二个参数不同的定义不同:

partial_sort需要一段左闭右开[)区间,vecStudents.begin()+10实际是第11个元素。找出有序的最好的前n个元素。

nth_element需要标识出容器中的某个位置。找出不关系顺序的最好的前n个元素。

当等级有相同时,假如一级有5名,二级有12,那么怎样在二等级的12名学生中选出5名,对于此上面两个函数有自己的想法,你无法控制。

这时候暗箱操作一下,你是教计算机的老师,你希望计算根据C++单科成绩靠前的来(你早就想到了这一天,你都学生们打分的时候就没有重复的),你可以重写一个按C++单科比较的比较函数,做一个全排列,然后再用上面的两个函数排出前10个,这时候你发现一个问题,可能选出的5个人不是C++单科成绩靠前的,因为partial_sort、nth_element都不是稳定排序的操作。

小私心满足不了那就换种策略吧,你想要把第一、二等级的所有学生都算上。当然可以使用一次全排序,然后找到第一个比二等级差的学生的位置,那么从起始位置到这个位置之间的学生就是你想要的。

然而全排序需要多做一些不要的事情,一个更好的策略时使用partition,partition可以把所有满足条件的元素都放在前面:

你需要先将之前的比较函数修改成比较这个学生的等级是否好于某一等级

 partition调用之后把所有满足条件的都放在了[begin(),goodEndIter)的区间中,如果对于同等级的需要保持之前的相对位置,可以使用stable_partition。

总结
sort、stable_sort、partial_sort、nth_element需要随机访问迭代器。

partition、stable_partition需要前向访问迭代器。

对于vector、string、deque、array和数组连续内存的容器:全排序可以使用sort、stable_srot;只需要对等价性最前面的n个元素进行排序使用partial_sort,不需要排序的话使用nth_element。

对于list、forward_list:排序只能使用其成员sort(这个是稳定的)。

对于序列容器(包括list,forward_list):按照是否满足某个区间分分开来,使用partition、stable_partition。

对于rb_tree关联容器的元素本来是有序的;

对于hashtable的关联容器,是通过hash值和单链表组织在一起的,不能排序。


 

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

u010787096

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值