跳转到内容

渐近复杂度与主定理

复杂度是衡量算法的尺子。本章讲大 O、Ω、Θ 的定义,递归式的三种求解方法(代入法、递归树、主定理),常见复杂度类的直观规模,以及常数因子何时重要。

记号含义直觉
O(g)O(g)渐近上界"不比 gg 慢"(最坏情况的界)
Ω(g)\Omega(g)渐近下界"不比 gg 快"(最好情况的保证)
Θ(g)\Theta(g)渐近紧界"与 gg 同阶"

严格定义:f(n)=O(g(n))f(n) = O(g(n)) 表示存在常数 c,n0c, n_0,使 n>n0n > n_0 时 f(n)≤c⋅g(n)f(n) \le c \cdot g(n)。三个使用规范:

  • 渐近记号隐藏常数与低阶项——3n2+100n=O(n2)3n^2 + 100n = O(n^2)。这在算法比较时是特性(聚焦增长趋势),在工程判断时是陷阱(见下文"常数何时重要")。
  • 说 OO 时通常指最坏情况:快排最坏 O(n2)O(n^2)、平均 O(nlog⁡n)O(n \log n),两个数各有用处,混用会出错。
  • 输入规模 nn 的定义要明确:对数算法说"O(log⁡n)O(\log n)"时,nn 是数值还是位数差一个指数——判断素数的朴素算法是 O(n)O(\sqrt{n})(按数值),按输入位数是 O(2b/2)O(2^{b/2})(指数)。密码学的"安全强度"永远按位数说(→ 公钥密码与密钥交换)。

分治算法(→ 分治)的代价写成递归式 T(n)=aT(n/b)+f(n)T(n) = aT(n/b) + f(n)。三种解法:

猜出答案(如 O(nlog⁡n)O(n \log n)),用归纳法验证并确定常数。最可靠,但需要先猜对。

把递归展开成树:每层代价 ff 之和,深度 log⁡bn\log_b n,逐层求和取近似。最直观,是主定理的推导来源。

对 T(n)=aT(n/b)+f(n)T(n) = aT(n/b) + f(n)(a≥1,b>1a \ge 1, b > 1),比较 f(n)f(n) 与 nlog⁡ban^{\log_b a}:

  • f(n)=O(nlog⁡ba−ε)f(n) = O(n^{\log_b a - \varepsilon}):T(n)=Θ(nlog⁡ba)T(n) = \Theta(n^{\log_b a})(叶子主导);
  • f(n)=Θ(nlog⁡balog⁡kn)f(n) = \Theta(n^{\log_b a} \log^k n):T(n)=Θ(nlog⁡balog⁡k+1n)T(n) = \Theta(n^{\log_b a} \log^{k+1} n)(逐层均匀);
  • f(n)=Ω(nlog⁡ba+ε)f(n) = \Omega(n^{\log_b a + \varepsilon})(正则条件):T(n)=Θ(f(n))T(n) = \Theta(f(n))(根主导)。

例:归并排序 T(n)=2T(n/2)+Θ(n)T(n) = 2T(n/2) + \Theta(n),nlog⁡22=nn^{\log_2 2} = n,第二类得 Θ(nlog⁡n)\Theta(n \log n)。

主定理只覆盖 T(n)=aT(n/b)+f(n)T(n) = aT(n/b) + f(n) 形式:子问题规模不均(如 T(n)=T(n/3)+T(2n/3)+nT(n) = T(n/3) + T(2n/3) + n)或非常规(T(n)=n T(n)+nT(n) = \sqrt{n}\,T(\sqrt{n}) + n)要回到递归树或代入法。

复杂度n=106n = 10^6 时的量级典型算法
O(log⁡n)O(\log n)~20二分查找
O(n)O(n)10610^6线性扫描、BFS/DFS
O(nlog⁡n)O(n \log n)2×1072 \times 10^7归并排序、堆排序
O(n2)O(n^2)101210^{12}(不可行)朴素排序、简单 DP
O(2n)O(2^n)天文数字子集枚举

经验法则:每秒 10810^8 次基本操作。竞赛与工程估算都用这张表——O(n2)O(n^2) 在 n=105n = 10^5 时已经不可行,必须找 O(nlog⁡n)O(n \log n) 或 O(n)O(n)。

渐近分析忽略常数,但工程上常数真实存在:

  • 小输入:O(nlog⁡n)O(n \log n) 的归并排序在小数组上输给 O(n2)O(n^2) 的插入排序——低阶项与常数在 n<30n < 30 时主导。这就是内省排序与 TimSort 在小区间切换插入排序的原因(→ 排序与查找)。
  • 缓存与向量化:理论更慢但缓存友好的算法(B+ 树 vs 红黑树)在实际中常胜(→ 二叉搜索树与平衡树)。
  • 正确的用法:用渐近记号做"增长趋势"的判断,用基准测试做常数因子的判断——两者缺一不可(→ 性能工程与可观测性)。
  • OO 是上界、Ω\Omega 是下界、Θ\Theta 是紧界;渐近记号隐藏常数与低阶项
  • 主定理只覆盖 T(n)=aT(n/b)+f(n)T(n) = aT(n/b) + f(n);其他形式用递归树或代入法
  • 输入规模 nn 的定义要明确(数值还是位数),否则对数复杂度会差一个指数
  • 常数因子在小输入、缓存与向量化面前真实存在:渐近定方向,基准测定常数