“Fibonacci Heap以更复杂的不变量保证 insert、meld、decrease key 摊还 $O(1)$;二项堆则按度立即 consolidation,meld 与 delet…”
形式陈述 ​
接口层 ​
优先队列接口扩展为 make-heap、find-min、insert、meld、decrease-key 和 delete-min。Meld 应避免逐个搬运全部元素;decrease-key 通常接收稳定句柄,否则重复键无法定位对象。
接口不承诺成本。二叉堆最小查询
直觉
可并优先队列把两批有序竞争者的合并当作一级操作,而不是逐元素重新插入。不同堆结构只是在“何时整理同阶树或恢复秩不变量”上分配成本:立即整理给出直接最坏界,延迟整理则用势能换取便宜 meld 与 decrease-key。
例子与边界
事件队列合并 ​
两个模拟器各维护事件堆,组件连接后需合并队列。数组堆拼接后线性 heapify 适合偶发合并,却不支持频繁亚线性 meld;树形堆可连接根表,把整理延后到 delete-min。
Meld 后外部句柄仍须有效。复制节点或重新编号会使句柄悬空。重复优先级要把键与对象身份分开,稳定性也不是 ADT 自动提供。
工程边界 ​
只需 push/pop 且缓存局部性重要时,二叉堆常更快。持久化、并发与最坏延迟是额外轴,不能从“可并”推出。
Dijkstra 若用“插入新距离、弹出时忽略旧条目”代替稳定句柄上的 decrease-key,正确性可以保留,但堆大小与操作序列已改变。比较理论界或内存占用时,必须注明采用哪一种接口实现。
操作语义与句柄生命周期 ​
Insert 返回指向逻辑节点的句柄;meld 后句柄仍必须定位同一对象;decrease-key 修改键并恢复堆序;delete 可通过 decrease 到负无穷再 delete-min,前提是键域允许哨兵,否则需要原生删除。重复键时句柄而非键值区分对象。
两个二项堆根阶分别为
推论与应用
可并堆常把结构整理延迟到 delete-min 或关键切割,因而需要摊还分析区分单次尖峰与长期操作序列成本。接口支持 meld 不等于 meld、decrease-key 与 delete-min 都有相同保证。
Pairing Heap以多叉堆和配对合并实现 meld、insert 与 delete-min,代码短且常有良好局部性能。它与 Fibonacci 堆共享可并接口,却不共享所有已知摊还界,尤其不能只凭相似的切割操作宣称同样的 decrease-key 理论保证。
成本来源 ​
二项堆 meld 扫
这些是摊还结论。要求每次 delete-min 最坏对数时需更严格结构;只写“Fibonacci heap 操作更快”会掩盖延迟清理和缓存局部性。
选择边界 ​
Dijkstra 中 decrease-key 多,理论改进可能重要;事件模拟只有 insert/delete-min 时,数组堆连续存储常更快。Pairing heap 代码简单、实测好,但部分 decrease-key 理论界与 Fibonacci heap 不同。接口相同不表示保证表相同。
参考资料
- Michael L. Fredman and Robert Endre Tarjan, “Fibonacci Heaps and Their Uses in Improved Network Optimization Algorithms,” Journal of the ACM 34(3), 1987, pp. 596–615.
- Robert Endre Tarjan, Data Structures and Network Algorithms, Society for Industrial and Applied Mathematics, 1983.
- Michel X. Goemans, Fibonacci Heaps, MIT 6.854J/18.415J Advanced Algorithms, Fall 2008, lecture notes.