关于第一版和双路快速排序的差异

关于第一版和双路快速排序的差异

  1. 老师关于第一版的快速排序算法和双路快速排序在时间性能的差异主要就是在于针对数组中元素都相同的情况,双路快速排序更加高效,其他情况两者差距不是很大是吗?

  2. 双路快速排序的优化是不是就是主要在于针对元素相同的情况,我们同时交换并移动了指针,从而平均分配了下一次迭代的空间,进而优化了时间?如果像下面这种写法,这种性能优化是不是就没有了?

相关代码:

while (left <= right) {
    if (array[left] < pivot) {
        left++;
    } else if (array[right] >= pivot) {
        right--;
    } else {
        swap(array, left++, right--);
    }
}


正在回答

登陆购买课程后可参与讨论,去登陆

1回答

1)


是的,双路快速排序的思路主要是为了避免在存在大量相同元素的情况下,第一版排序(我称之为单路快排:))的退化。


如果你确定你处理的数据不包含大量重复数据,甚至没有重复数据,使用单路快速排序足够(甚至更优,因为单路快速排序内部无论是变量的数量,还是 if 判断的数量,都更少,常数级开销更小。)



2)


非常非常赞!是的。一旦比较里有了等号,双路快排也会退化。


印象里这一点在课程中提及过。但我强烈建议大家具体实验一下,课程代码中:https://git.imooc.com/class-105/Play-Algorithms-and-Data-Structures/src/master/12-More-about-QuickSort/03-QuickSort-2-Ways/src/QuickSort.java

66 行和 69 行的 arr[i].compareTo(arr[l]) < 0 和 arr[j].compareTo(arr[l]) > 0 如果改成 <= 和 >=,会发生什么?



也正因为如此,双路快排虽然看起来思想简单,但其实实现起来非常容易出错,乃至甚至很多教科书根本不介绍这个思路。因为,在实践中,可以使用双路快排的地方,也就可以使用三路快排。如果要避免所有的快排过程中可能发生的退化情况,三路快排更常用:)(三路快排课程后续会介绍。)



继续加油!:)

  • hxcchan 提问者 #1

    谢谢老师,我突然想到如果数据的size预先是不可知的,是以流数据的形式不停传入进来,那这种情况是不是单路快速排序就用得上了(online algorithm),因为不需要像双路快速排序那样预先知道数组最后一个元素的位置。但是我不知道会不会有针对这种情况的排序需求,还是大部分情况排序都是size确定好的。

    2022-01-25 03:08:20
  • liuyubobobo 回复 提问者 hxcchan #2

    不可以。快速排序本身就是离线算法,不管是几路。因为在找到了标定点之后(pivot),必须完整知道所有的其他元素相较标定点的大小关系,才能继续递归排序下去。

    2022-01-25 04:47:24
问题已解决,确定采纳
还有疑问,暂不采纳

恭喜解决一个难题,获得1积分~

来为老师/同学的回答评分吧

0 星
算法与数据结构
  • 参与学习       2583    人
  • 解答问题       1082    个

慕课网算法名师Liuyubobobo,5年集大成之作 从0到工作5年,算法与数据结构系统解决方案

了解课程
请稍等 ...
意见反馈 帮助中心 APP下载
官方微信

在线咨询

领取优惠

免费试听

领取大纲

扫描二维码,添加
你的专属老师