使用主定理求解遞歸式
主定理是分治算法分析中非常重要的定理。
如,我們要處理一個 規模為 \(n\) 的問題通過分治,得到 \(a\) 個規模為 \(\dfrac{n}{b}\) 的問題,分解子問題和合並子問題的時間是 \(f(n)\)。
在 \(T(n) = aT(\frac{n}{b})+f(n)\) 這個式子里,要求 \(a \geqslant 1, b> 1\)(如果 \(b=1\) 時,遞推無意義),\(f(n)\) 是漸進意義上的正數。
回顧一下 \(a\) 和 \(b\) 的含義:
- \(a\) 個子問題,即 \(a\) 是原問題分為子問題的個數;
- 每個子問題的規模是 \(\dfrac{n}{b}\);
- 分治算法共三部分,分治合,而 \(f(n)\) 就是分 + 合的時間。\(\left \lfloor \frac{n}{b} \right \rfloor\) 和 \(\left \lceil \frac{n}{b} \right \rceil\) ,向下取整和向上取整的細節,並不會影響主定理的推導。
而后呢,根據上面的式子我們會得到三種情況:
- 若有實數大於零 \((\varepsilon >0),f(n)=O(n^{\log_{b}a-\varepsilon})\),則 \(T(n)=\Theta (n^{\log_{b}a})\);
- 若 \(f(n)=\Theta (n^{\log_{b}a})\),則 \(T(n)=\Theta (n^{\log_{b}a}\log_n)\);
- 若有實數大於零 (\(\varepsilon >0)\)\(f(n)=\Omega (n^{\log_{b}a+\varepsilon })\),使得較大的 \(n\),滿足 \(af(\frac{n}{b})\leqslant cf(n)\),這時候則 \(T(n) = \Theta (f(n))\)。
這三種情況看起來很復雜,搞清楚他們之間的關系,快速記憶就簡單了。
對於三種情況的每一種,我們將函數 \(f(n)\) 與 \(n^{\log_{b}a}\) 比較,倆個函數較大者將決定遞歸式的解。
-
若函數 \(n^{\log_{b}a}\) 更大,如情況 \(1\),則解是 \(T(n)=\Theta (n^{log_{b}a})\);注意 \(f(n)\) 小於 \(n^{\log_{b}a}\) 是漸進意義上的,要差一個因子量級 \(n^{\varepsilon }(\varepsilon >0)\)。
-
若函數 \(f(n)\) 更大,如情況 \(3\),則解是 \(T(n) = \Theta (f(n))\);注意 \(f(n)\) 大於 \(n^{\log_{b}a}\) 是漸進意義上的,要差一個因子量級 \(n^{\varepsilon }(\varepsilon >0)\),還要滿足 \(af(\frac{n}{b})\leqslant cf(n)\);
-
若倆個函數相等,如情況 \(2\),則乘上一個對數因子,解為 \(T(n)=\Theta (n^{\log_{b}a}~\log_n)\);
-
上面的三種情況並未覆蓋 \(f(n)\) 的所有可能性,情況 \(1\)、情況 \(2\) 之間存在間隙,\(f(n)\) 可能小於 \(n^{\log_{b}a}\) 但不是多項式意義上的小於;情況 \(2\)、情況 \(3\) 之間也存在間隙,\(f(n)\) 可能大於\(n^{log_{b}a}\) 但不是多項式意義上的大於;若函數 \(f(n)\) 在這倆個間隙中,或者是情況 \(3\) 中要求的 \(af(\frac{n}{b})\leqslant cf(n)\) 條件不成立,就不能使用主方法來解決遞歸式。
首先,得明白一個基准函數:\(\Theta (n^{log_{b}a})\)。
有了基礎函數之后,就可以根據它來判定情形之間的關系。
那我們該如何記憶這個基准函數呢 ??
原來的函數是:\(aT(\frac{n}{b})+f(n)\) 為底數,如果化為對數形式也是以 \(b\) 為底 \((\log_{b}a)\);
原函數是一個多項式,\(a\) 和 \(b\) 都是常數,算出來肯定也是一個具體的數值。
所以,我們要記這樣一個基准多項式(基准函數):\(\Theta (n^{?})\),次方(即 \(?\))是取對數的。
接下來,是以上三種情況的判定:
- \(f(n)\) 是弱於基准的,\(O(n^{\log_{b}a-\varepsilon })<\Theta (n^{\log_{b}a})\);
- \(f(n)\) 是等於基准的,\(\Theta (n^{\log_{b}a})=\Theta (n^{\log_{b}a})\);
- \(f(n)\) 是強於基准的,\(\Omega (n^{\log_{b}a+\varepsilon })>\Theta (n^{\log_{b}a})\)。
例子
例 \(1\):\(T(n)=4T(\frac{n}{4})+\Theta (1)\)(樂高鋪積木)
分析,\(a=b=4\),基准函數是 \(\Theta (n^{\log_{4}4})\),因為 \(\log_{4}4=1\),所以基准函數是 \(\Theta (n)\)。
又因為 \(f(n) = \Theta (1)\) 比基准函數 \(\Theta (n)\) 要弱,我們取一個實數 \((\varepsilon=1)\),即 \(\Theta (1)=O(n^{1-\frac{1}{2}}) = O(\sqrt{n})\)。
得到 \(T(n)=\Theta (n )\)。
例 \(2\):\(T(n)=T(\frac{n}{2})+\Theta (1)\)(二分查找)
分析,\(a=1,b=2\),基准函數是 \(\Theta (n^{\log_{2}1})\),因為 \(\log_{2}1=0\),所以基准函數是 \(\Theta (1)\)。
又因為 \(f(n)=\Theta(1)\),基准函數也是 \(\Theta(1)\) ,\(f(n)=\) 基准函數,再乘上一個 \(\log n\),即 \(T(n)=\Theta(\log n)\)。
例3:\(T(n)=2T(\dfrac{n}{2})+\Theta(n)\) (歸並排序)
分析,\(a=b=2\),基准函數是 \(\Theta (n^{\log_{2}2})\),因為 \(\log_{2}2=1\),所以基准函數是 \(\Theta (n)\)。
又因為 \(f(n)=\Theta (n)\),基准函數也是 \(\Theta (n)\),\(f(n)=\) 基准函數,最后 \(T(n)=\Theta (n~logn)\)。