演算法分析是對乙個演算法需要多少計算時間和儲存空間作定量分析。此文主要介紹如何使用漸近分析記號來表示演算法的時間複雜度以及如何對演算法效率進行比較。
輸入規模度量
執行時間的度量單位
演算法的最優、最差和平均效率
小規模輸入在執行時間上的差別不足以將高效演算法和低效演算法區分開來。乙個需要指數級操作次數的演算法只能用來解決規模非常小的問題。
指數增長是恐怖的,例如\(n^2\)和\(2^n\),當規模增加一倍,\(n \to 2n\),那麼對於\(n^2\)來說,執行時間只是增加4倍,而對於\(2^n\)來說,卻是增加了\(2^n\)倍,這個倍數與n有關。
常數間的差異較小,在表示演算法時間複雜度時我們通過省略常數對表示式的影響,如:\(100n^2\)、\(1.5n^2\)、\(n^2+4\)、\(10n^2-3n+6\),我們都看成是相等的。
演算法效率的主要指標是基本操作次數的增長次數。為了對這些增長次數進行比較和歸類,計算機科學家們使用了3種符號:
漸近上界符\(o\)
存在正常數\(c\)和\(n_0\),使得對所有\(n \ge n_0\) ,有
\[f(n) \le cg(n)
\]記為\(f(n) \in o(g(n))\)
如,\(n \in o(n^2)\) ,\(100n+5 \in o(n^2)\),\(n(n-1)/2 \in o(n^2)\)
漸近下界符\(\omega\)
存在正常數\(c\)和\(n_0\),使得對所有\(n \ge n_0\),有
\[f(n) \ge cg(n)
\]記為\(f(n) \in \omega(g(n))\)
如,\(n^3 \in \omega(n^2)\),\(n(n+1) \in \omega(n^2)\),\(4n^2+5 \in \omega(n^2)\)
漸近近界符\(\theta\)
存在正常數\(c_1\),\(c_2\)和\(n_0\),使得對所有\(n \ge n_0\),有
\[c_2g(n) \le f(n) \le c_1g(n)
\]記為\(f(n) \in \theta(g(n))\)
如,\(n^2+3n+2 \in \theta(n^2)\),\(n(n-1)/2 \in \theta(n^2)\) ,\(4n^2+5 \in \theta(n^2)\)
定理:如果\(t_1(n) \in o(g_1(n))\) 並且\(t_2(n) \in o(g_2(n))\) ,則
\[t_1(n)+t_2(n) \in o(max\)
\]對於符號\(\theta\)和\(\omega\),該定理也成立。該定理表示:當演算法由兩個連續執行部分組成時,該演算法的整體效率由具有較大增長次數的那部分所決定。
我們使用\(f(n)=o(g(n))\)來表示\(f(n)\)是\(o(g(n))\)的乙個成員函式,而不用傳統的\(f(n) \in o(g(n))\)來表示,是因為習慣問題。
例如,\(f(n)=5n^3;g(n)=3n^2;f(n)=o(n^3)=g(n)\) 但是\(f(n) \ne g(n)\)
因此,\(f(n)=\theta(g(n))\)的確切意義是:\(f(n) \in \theta(g(n))\)。一般情況下,\(\theta(g(n))\)表示的是\(\theta(g(n))\)中的某個函式。如,\(2n^2+3n+1=2n^2+\theta(n)\) 表示\(2n^2+3n+1=2n^2+f(n)\),其中\(f(n)\)是\(\theta(n)\)中某個函式。
傳遞性反身性
對稱性\(f(n)=\theta(g(n)) \leftrightarrow g(n)=\theta(f(n))\)
互對稱性
\(f(n)=o(g(n)) \leftrightarrow g(n)=\omega(f(n))\)
\(f(n)=o(g(n)) \leftrightarrow g(n)=\omega(f(n))\)
算術運算
\(f(n)+g(n)=o(max\)\);
\(f(n)+g(n)=o(f(n)+g(n))\);
\(f(n)*g(n)=o(f(n)*g(n))\);
\(cf(n)=o(f(n))\);
\(g(n)=o(f(n)) \rightarrow g(n)+f(n)=o(f(n))\);
常數\(c\)
< 對數\(logn\)
< \(log^2n\)
< 線性\(n\)
< \(nlogn\)
< 平方\(n^2\)
< 立方\(n^3\)
< 指數\(2^n\)
< 階乘\(n!\)
< \(n^n\)
線性時間 \(o(n)\)
執行時間只是輸入大小的乙個常數倍數。
如,求n個數中最大數問題;合併兩個有序的序列;
\(o(nlog(n))\)時間
\(o(nlog(n))\)時間多出現在分治演算法中。如合併排序、堆排序都將產生\(o(nlog(n))\)時間。
平方時間 \((o^2)\)
如,列舉所有元素對;求平面上n個點中最近的兩個點之間的距離。
多項式時間 \(o(n^k)\)
指數時間
最大獨立集問題:給出乙個圖,求最大的乙個點集使得其中任何兩個點都不存在一條邊。窮舉搜尋產生執行時間\(o(n^22^n)\)的演算法。
定義法找到正常數\(c\)和\(n_0\)使得對所有\(n\ge n_0\),有\(f(n) \le cg(n)\),則\(f(n)=o(g(n))\)
極限法,若
\[\lim\limits_=0}
\]則,\(f(n)=o(g(n))\).
取對數法
對於比較難比較的兩個數,我們可以先對它們同時取對數後進行比較。但是要注意,取完對數後的常數是不能忽略的。
開學三個月後,終於有時間寫部落格了~
排序演算法複雜性
穩定排序與不穩定排序 假設 ki kj 且排序前序列中 ri 領先於 rj 若在排序後的序列中 ri 仍領先於 rj 則稱排序方法是穩定的。若在排序後的序列中 rj 仍領先於 ri 則稱排序方法是不穩定的。演算法的複雜性 體現在執行該演算法時的計算機所需資源的多少上,計算機資源最重要的是時間和空間 ...
演算法時間複雜性歸納
註明出處 部落格原文 這一段很清晰的說明了時間複雜性的計算,已註明出處。下面分別對幾個常見的時間複雜度進行示例說明 1 o 1 temp i i j j temp 以上三條單個語句的頻度均為1,該程式段的執行時間是乙個與問題規模n無關的常數。演算法的時間複雜度為常數階,記作t n o 1 注意 如果...
《計算複雜性與演算法分析》和《計算複雜性》學習
今天偶然間碰到數學界著名的七大千禧難題,關注了p和np問題,但是裡面提到關於演算法的複雜性的描述已經超出了自己的知識範圍,我找到了一本書來彌補這個不足,即 計算複雜性與演算法分析 希望自己在看完這本書之後能夠對計算複雜性有完整的概念 首先看看它的目錄 其實大部分的知識都有接觸過,但是沒有形成體系 接...