ref:
攤還分析是用來評價程式中的乙個操作序列的平均代價,有時可能某個操作的代價特別高,但總體上來看也並非那麼糟糕,可以形象的理解為把高代價的操作「分攤」到其他操作上去了,要求的就是均勻分攤後的平均代價。
攤還分析有三種常用的技術;聚合分析,核算法,勢能法。
首先看個例子,現在有三種操作,push(s),pop(s),mutlipop(s,k),push(s),統稱為棧操作。 push(s)每次只能壓乙個資料,所以規定操作的代價為1,pop(s)每次只能彈乙個資料,所以也規定操作的代價為1,而mutlipop(s,k),內部實現的是乙個迴圈彈出,每執行一次的代價為k(k為棧的最大容量)。那麼現在問題來了,我想分析下執行n次棧操作最壞情況下的時間複雜度是多少?第一反應應該就是這樣想的,mutlipop(s,k)的代價最高,最高位k=n;
執行n次的最壞情況當然就是o(n2)啦,當實際上並非如此。
聚合分析要求我們要總體看問題,首先mutlipop(s,k)也是個彈棧的操作,當棧裡有資料的時候才執行有效,所以上述提到的o(n2)是不科學的,而push(s),pop(s)的代價是1,可想而知最壞的情況當然是前n-1次操作都是壓棧,而最後一次才執行mutlipop(s,n-1),這樣的代價也只有2n-2,時間複雜度為o(n),平均下來每個操作的攤還代價就為o(1)了。
核算法比較好理解,進行攤還分析時,攤還的代價有可能多於實際的代價,也有可能少於實際的代價,多於實際代價的差額會存進乙個資料結構中,稱為信用,而當遇到少於實際代價的時候就可以用這些信用來填充了。注意這些什麼演算法提供的只是思路,求出一系列操作代價的上界的思路,具體的做法還是要自己思考的。
同樣是壓棧的例子,我們可以賦給push(s)操作的攤還代價是2,相當於自己使用了1,而壓進去的必定會彈出,剩下的1就作為彈出時的費用,這樣pop(s)和mutlipop(s,k)的攤還代價就為0,這樣做有什麼意義?試著現在思考下題目中的問題(標紅色的部分),那麼可想最糟糕的情況無非就是所有操作都是push(s),代價為2n,並不像聚合代價那樣需要考慮其他兩個操作(攤還代價為0),時間複雜度為o(n)。
勢能法
勢能法其實核算法有點相似,也有預付差額的,但不叫信用,而叫勢能,勢能法是從整體上看的,不像核算法那樣具體到某個操作,而是整體的勢能。
勢能法定義了一條公式;
ci(攤還)=ci(實際)+f(di)-f(di-1) (1)
累加可得總攤還代價的公式為;
ci(總攤還)= ci(總實際)+ f(di)-f(d0) (2)
其中ci
為每步操作的代價,f(di)表示執行了第i個操作後的勢能,那個這個公式就可以理解為 第i步操作的攤還代價等於第i步操作的實際代價加上從第i-1步操作到第i步操作的勢能變化,理解這個後,再來看棧操作的例子。
同樣push(s)、pop(s)的代價為1, mutlipop(s,k)的代價為k,我們規定入棧乙個元素勢能加1,彈出乙個元素勢能減1,那麼f(di)永遠為非負,而f(d0)等於0,再根據上面的公式(2)即可知道這個又這裡就可以確定總攤還代價是總實際代價的上界,所以現在要求的就是總攤還代價。
根據公式(1)可以得到push(s)的攤還代價為2,pop(s)的攤還代價為0,mutlipop(s,k)的攤還代價也為0 (因為彈棧勢能要減,剛好和代價抵消,也可以看做勢能都用來支付代價了,所以下降了),那麼又回到了核算法了,可得時間複雜度為o(n)。
書上還有個例子是關於表擴張的,雖然能看懂,但還是理解的不太透徹(不明白他為什麼能這麼定義),在這裡跟大家分享,也請大家指點~
例子:表擴張
是這樣的,有個程式,假設這個表只允許插入,當插入資料發現表滿了,會自動新建乙個表大小為原來的兩倍,然後把已有的資料複製過去,再插入,在問題就是要求這個程式的代價,準確來說是攤還代價。
這裡只寫兩個方法吧,寫多我自己都暈了..首先是聚合分析
我們將插入一條資料的代價看為1,假設一開始表的大小為1,沒有資料,可想除了表資料滿的情況,其他情況的代價都為1,而表滿時的大小都為2的冪。當表滿時插入資料的代價就是原有的資料複製的代價k(假設有k條資料)加上新插入的1條,又此可得總攤還代價為
c(總攤還代價)<=n+20 +21+..+2lgn
其中lgn表示表共擴張了lgn次,可以算出),所以攤還代價至多為3n/n=3
下面看看核算法,通過核算法能很好的理解為什麼攤還付代價為3.
書上是這樣分析的,假設現在表中有m/2條資料,表大小為m,而且沒有信用,那麼插一條資料要付出3的代價,為什麼?看,1是為了插入時消耗了,1是儲存起來作為自己的信用,還有1呢,就是捐贈跟原本就在表中但沒有信用的資料,這樣,但資料插入了m/2條,一共有m條資料時,這也剛好是表要擴張的時候,表中所有的資料都有1的信用,就可以用來支付擴充套件表時複製到新錶的代價,從而表的大小變成2m,資料剛好又沒了信用而且剛好是表大小的一半,這又到回了最初,就好像遞迴一樣,也就是說1條資料支援3代價就可以保證它永遠的擴充套件…
攤還分析 1 演算法導論 23
攤還分析 amortized analysis 是一種分析乙個操作序列中所執行的所有操作的平均時間分析方法。與一般的平均分析方法不同的是,它不涉及概率的分析,可以保證最壞情況下每個操作的平均效能。下面介紹癱瘓分析中的最常用的三種技術。先來看對棧進行操作的例子。通常,棧能夠進行push s,x 與po...
演算法導論第17章 攤還分析
在攤還分析中,我們求資料結構的乙個操作序列中所執行的所有操作的平均時間,來評價操作的代價,從而說明乙個操作的平均代價是很低的,即使序列中某一單一操作的代價很高,不涉及改了,但可以保證最壞情況下每個操作的平均時間。攤還分析中主要的三種方法 1 聚合分析 2 核算法 即記賬法 3 勢能法 1 聚合分析 ...
演算法導論學習筆記之攤還分析
在攤還分析中,我們求資料結構的乙個操作序列中所執行的所有操作的平均時間,來評價操作的代價。這樣,就可以說明即使乙個序列的某個操作很複雜,平均代價還是很低的。攤還分析中最常用三種技術 聚合分析,這種方法用來確定乙個n個操作的序列的總代價的上界t n 因而每個操作的代價是t n n,將平均代價作為每個操...