希尔排序:更佳的序列
看完你能说清邮资问题、逆序对如何决定增量序列的性能上限
按 空格/→ 演示下一步
全部页面点击任意一页,跳回舞台从这页播放
希尔排序:更佳的序列
看完你能说清邮资问题、逆序对如何决定增量序列的性能上限
序列问题是什么
上一页我们看到:希尔排序的框架是固定的——按间隔分组做插入排序,间隔逐轮缩小到 1。但间隔每轮取多少、怎么缩小,框架并没有规定。这个自由度,正是本节要解决的问题。
大火收汁后转小火;每档火候的安排决定菜能不能炒好
好序列的评判标准
这棵思维导图列出评判增量序列好坏的四个维度,从左到右逐条展开,先看根再看分支。
什么是逆序对
上一页我们说要给序列「减少混乱」,但混乱怎么量化?想想排队:前面的人比后面高,大家看着就别扭。这种「该在后面的却在前面」的组合,就是衡量乱程度的基本单位。
队伍里前面的人比后面高,一对就是一组合
数逆序对的例子
以小数组为例逐步找出所有逆序对
逆序对与插入排序
上一页我们数过逆序对,它就是数组「乱的程度」。那排序到底在干什么?答案很干净:就是在消灭逆序对。而插入排序每交换一次,恰好只消掉一个。
让插队的人一格格挪回去,每挪一格只解决一对冲突
逆序对视角看希尔排序
从上往下读:每趟增量削减一批逆序对,越往下剩余越少,最后一趟几乎不用干活。
逆序对计数实现
用归并排序在 O(n log n) 内数出逆序对,量化序列好坏。
归并时三处计数相加:左半内部、右半内部、跨越中线的逆序对;右半元素落位时,左半剩余个数一次性统计,避免逐对比较。
邮资问题是什么
上一页我们看完了几种经典的增量序列,但你可能好奇:为什么 3h+1 这样的序列特别受推崇?这要从一个看似无关的老问题说起——邮票怎么贴,才能恰好凑出某个邮资。
邮票面额对应增量步长,能否凑齐所有金额对应能否均匀打乱全表
邮资问题的求解过程
用 3 分和 4 分邮票凑出 14 分,一步步看组合如何构造出来。
邮资问题的启示
前面算过:1、5、12、19 这组邮票面值,在限额内几乎每个金额都能凑出——面值组合的“覆盖能力”是设计出来的。增量序列也一样:h 取哪些值,决定了哪些间隔的逆序对能被提前消掉。
面值要凑出所有金额,增量要消掉所有间隔的逆序对
邮资思路 vs 简单折半
两者都为希尔排序造增量序列,但出发点完全不同:一个凭几何直觉,一个靠计数证明。
- 出发点:覆盖所有可能的间隔需求
- 增量形如 2^k−1,相邻约两倍关系
- 性质:可证明约 O(n^1.5) 上界
- 出发点:直觉上快速缩小间隔即可
- 增量 n/2, n/4, …,相邻严格两倍
- 性质:最坏可退化到 O(n²)
定理K的陈述
邮资问题给了我们灵感:只用 2 的幂的倍数,硬币系统才「顺畅」。希尔排序的序列也一样挑剔——有一个著名定理(Pratt,1971)告诉我们什么样的序列能把界压到 O(N^{3/2})。
前一棒建立的领先优势(有序性)交棒时不丢,下一棒只需小步巩固
定理K证明思路
定理K的证明拆成四步:每步只依赖前一步的观察,逐层逼近结论。
定理K与逆序对的联系
左上顺主干:定理K条件如何一路转化为逆序对被高效削减;右下分支展示条件被破坏时的最坏结局。
自测:序列的取舍
关于希尔排序增量序列的条件,下列说法正确的是?
要点收束
- ✓逆序对数是插入排序成本的可视化账本
- ✓希尔排序每轮大幅消解逆序对,后续轮变轻松
- ✓邮资问题引出「可达增量序列」的设计约束
- ✓定理K保证:相邻增量互素时计数下界更优
- ✓好序列=每轮消得多,且轮间留有长程交换能力
课后思考
三个问题,先自己想五分钟,再看参考答案。
参考答案思考路径:h 排序后,任意间隔为 h 倍数的位置对都逆序消除;相邻步长结构互相“借力”。回想逆序对视角那页,看小步长如何继承大步长的成果。
参考答案没有唯一答案。可考虑:数据规模与大致有序程度、步长间最好互质(避免重复比较)、最坏情形上界(如定理K的 1,4,13 序列)、实现的简单性。
参考答案不成立。证明关键用到 4 与 13 的特定整除关系(如 13=3×4+1);换序列需重新推导。思考:互质步长为何破坏原有论证,邮资问题的启示又如何迁移。