有哪些 Big-O 表示法 [1] 在实践中失败的例子?
也就是说:算法的 Big-O 运行时间什么时候会预测算法 A 比算法 B 快,而实际运行时算法 B 会更快?
稍微宽泛一点:关于算法性能的理论预测何时与观察到的运行时间不匹配?非大 O 预测可能基于搜索树中的平均/预期旋转次数,或排序算法中的比较次数,表示为因子乘以元素数量。
澄清:
尽管有些答案说了什么,但 Big-O 表示法旨在预测算法性能。也就是说,它是一个有缺陷的工具:它只谈论渐近性能,它模糊了常数因素。它这样做是有原因的:它旨在预测算法性能,而与您在哪台计算机上执行算法无关。
我想知道的是:这个工具的缺陷什么时候表现出来?我发现 Big-O 表示法相当有用,但远非完美。有哪些陷阱、边缘情况和陷阱?
我正在寻找的一个例子:使用斐波那契堆而不是二进制堆运行 Dijkstra 的最短路径算法,你得到 O(m + n log n) 时间与 O((m+n) log n),对于 n顶点和 m 条边。您预计斐波那契堆迟早会提高速度,但在我的实验中从未实现过速度提高。
(没有证据的实验证据表明,在均匀随机边权重上运行的二进制堆花费 O(1) 时间而不是 O(log n) 时间;这是实验的一个大问题。另一个难以计数的问题是预期的调用 DecreaseKey 的次数)。
[1] 实际上,失败的不是符号,而是符号所代表的概念,以及预测算法性能的理论方法。</反迂腐>
关于接受的答案:
我已经接受了一个答案,以突出我希望得到的答案。存在许多同样好的答案:) 我喜欢这个答案的地方在于,它提出了一个通用规则,用于何时 Big-O 表示法“失败”(当缓存未命中主导执行时间时),这也可能增加理解(在某种意义上我不确定如何最好地表达 ATM)。