謎題:一個在實務中很棒的「壞」演算法
這裡有個最壞情況分析無法解釋的故事。線性規劃的單純形法在最壞情況下是指數的:存在人工精心構造的輸入(Klee-Minty 立方體),在上面它會在結束前走訪 2^n 個角點。按最壞情況大O的判決,它是個壞演算法。然而幾十年來它一直是最佳化的主力,眨眼間就解出含上百萬變數的真實實例。這兩件事都是真的。指數的例子確實存在;實務上的快速也是真的。那麼分析漏掉了什麼?
自然的反射動作是去抓平均情況分析:也許單純形法在「典型」輸入上很快。但平均情況有個惡名昭彰的弱點,我們在比較 最壞、最佳與平均情況 時就遇過了——它的答案完全取決於你假設的輸入分布。挑均勻隨機的矩陣得到一個數字;挑別的分布又得到另一個。真實世界的線性規劃並非從任何東西均勻隨機抽出;它們是有結構的、人為造出的物件。對一個沒人實際面對的分布取平均,什麼也解釋不了。我們需要一個既非惡意對手、也非整齊隨機源的輸入模型。
平滑的念頭:先讓對手出招,再輕輕一抖
平滑分析由 Spielman 與 Teng 在 2001 年提出,找到了一條漂亮的中道。讓對手挑它能想像到的最壞輸入——給它最大的權力,就像最壞情況分析那樣。然後,在演算法執行前,用一個微小的隨機量去擾動那個輸入:對每個數字都加上量級為 sigma 的、一點點獨立的高斯雜訊。平滑複雜度是最壞的期望執行時間,其中對手挑選基底實例,而期望值是對隨機擾動取的。它是個混血:外層是最壞情況的取最大,內層是平均情況的取期望。
為什麼一個微小的擾動是對的念頭,而不是作弊?洞見在於:最壞情況的實例通常很脆弱,平衡在刀鋒上:Klee-Minty 立方體仰賴的是以外科手術般精度對齊的角點。真實輸入是由感測器量得、捨入到有限精度、或由人類輸入的——它們總帶著一點雜訊。擾動是在問:那些壞實例經得起一推嗎,還是任何雜訊一碰就溶解?若壞情況構成一個薄到近乎消失、任何抖動都能逃離的集合,那麼最壞情況的界,描述的就是一個測度為零的幽靈,而不是你會遇到的輸入。
單純形法的回報,與一個誠實的解讀
Spielman 與 Teng 證出了那條頭條結果:單純形法(搭配合適的樞紐規則)的平滑複雜度,是變數數目與 1/sigma 的多項式。白話說:隨便拿任何一個線性規劃,加上一絲微弱的隨機雜訊,期望的單純形步數就是多項式——沒有任何 2^n 的爆炸能存活。那些指數立方體是真的,卻精緻得脆弱;最輕微的擾動就把它們粉碎了。這是對一個五十年老謎的第一個嚴謹解釋,並獲得 2008 年哥德爾獎與 2009 年富爾克森獎。它重新定義了判決:單純形法不是「一個運氣好的指數演算法」,而是一個其困難情況脆弱到無法發生的演算法。
現在是這一階要求的誠實。平滑分析不是免費的午餐,也沒有廢除最壞情況的思考。其一,它的保證是對擾動取的期望值——很像 隨機快速排序 的 O(n log n) 是期望時間,而它的最壞情況仍是 O(n^2)。單獨一個被擾動的實例仍可能慢;平滑說的是對雜訊取平均後很快。其二,這個界依賴 sigma:當雜訊縮向零時,多項式退化回指數的最壞情況,所以一個「多項式平滑界」帶來的安慰,只值你能誠實假設存在的那點雜訊量。其三,它把雜訊建模成獨立的高斯——一個乾淨的假設,真實的、相關的、有結構的擾動未必符合。
平滑分析會旅行:它是一面透鏡,不是一招把戲
單純形法是第一個凱旋,但這面透鏡能推廣到任何最壞情況看起來可疑地脆弱的演算法。兩個乾淨的例子。旅行推銷員的 2-opt 啟發式——一個你在這一階早先見過的 區域搜尋,它反覆交換兩條邊以縮短一趟巡迴——有指數的最壞情況執行時間,實務中卻幾乎瞬間就停。平滑分析證明了它:在被擾動的點座標下,期望的 2-opt 步數是多項式的。那些逼出長時間執行的、脆弱的對抗性巡迴,撐不過一抖。
第二個例子讓「哪個量被平滑」這一點更銳利。許多演算法的執行時間由一個「條件數」主宰,而這條件數只在輸入正好坐落於某種退化上時才會災難性地壞——一個恰好奇異的矩陣、三個恰好共線的點。擾動以壓倒性的機率把輸入推離那道刀鋒,於是期望的條件數、進而期望的執行時間,都變得溫馴。一再出現的主題與驅動整一階的那個一樣:純粹的最壞情況可能悲觀到 不再是個有用的嚮導,而超越最壞情況的模型存在的目的,正是要找回一個與現實相符的預測。
未竟之路:給全部五個前沿的一張地圖
退後一步,把整一階看成同一個念頭穿著五套戲服。每個前沿都從承認某處乾淨的古典模型會崩開始,然後改變了它認真對待的是哪個資源、或哪些輸入——並換來一個更銳利、更誠實的理論。它們是對同一個問題的五個答案:這裡真正的限制是什麼?
- 當被藏起的是未來、而非輸入規模時:線上演算法 必須在看見其餘部分之前就做出無法收回的決定,而 競爭比 衡量這份盲目相對於一個全知最佳解所付的代價。
- 當稀缺資源是記憶體、而非時間時:串流模型 在次線性空間下每個項目只看一次,而一個草圖(如 count-min 草圖)用可控的誤差換取極小的佔用。
- 當問題是 NP 困難、但有一個參數很小時:固定參數可解 把指數的爆炸關進那個參數 k 裡,給出 f(k) 乘上一個多項式,而非對整個輸入取指數。
- 當你根本負擔不起最佳性時:區域搜尋與元啟發式 靠改良鄰居來追逐一個夠好的解,誠實地冒著陷入一個並非全域最佳的區域最佳的風險。
- 當最壞情況真實卻脆弱時:平滑分析擾動對手的輸入,問那些困難情況是否存活——在純粹最壞情況絕望之處,找回一個多項式的預測。
而這條路確實在這一階之後延續。最深的開放問題 P 對 NP 至今仍未解決——我們仍無法證明,撐起這裡每個應對策略的那些 NP 困難問題,真的需要超多項式時間。更新的前沿推得更遠:細粒度複雜度問的不只是「是否多項式?」,而是某個特定的 O(n^2) 演算法在像強指數時間假設這樣的困難猜想之下能否被打破。整個階梯的誠實總結,不是「答案在此」,而是「該如何問對問題」:說清你真正的資源、說清你真正面對的輸入,並選一個會對它們說實話的模型。