一般實際生活中我們遇到的算法分為四類:
一>判定性問題
二>最優化問題
三>構造性問題
四>計算性問題
而今天所要總結的算法就是着重解決 最優化問題
《算法之道》對三種算法進行了歸納總結,如下表所示:
標准分治 |
動態規划 |
貪心算法 |
|
適用類型 |
通用問題 |
優化問題 |
優化問題 |
子問題結構 |
每個子問題不同 |
很多子問題重復(不獨立) |
只有一個子問題 |
最優子結構 |
不需要 |
必須滿足 |
必須滿足 |
子問題數 |
全部子問題都要解決 |
全部子問題都要解決 |
只要解決一個子問題 |
子問題在最優解里 |
全部 |
部分 |
部分 |
選擇與求解次序 |
先選擇后解決子問題 |
先解決子問題后選擇 |
先選擇后解決子問題 |
分治算法特征:
1)規模如果很小,則很容易解決。//一般問題都能滿足
2)大問題可以分為若干規模小的相同問題。//前提
3)利用子問題的解,可以合並成該問題的解。//關鍵
4)分解出的各個子問題相互獨立,子問題不再包含公共子問題。 //效率高低
【一】動態規划:
依賴:依賴於有待做出的最優選擇
實質:就是分治思想和解決冗余。
自底向上(每一步,根據策略得到一個更小規模的問題。最后解決最小規模的問題。得到整個問題最優解)
特征:動態規划任何一個i+1階段都僅僅依賴 i 階段做出的選擇。而與i之前的選擇無關。但是動態規划不僅求出了當前狀態最優值,而且同時求出了到中間狀態的最優值。
缺點:空間需求大。
【二】貪心算法:
依賴:依賴於當前已經做出的所有選擇。
自頂向下(就是每一步,根據策略得到一個當前最優解。傳遞到下一步,從而保證每一步都是選擇當前最優的。最后得到結果)
【三】分治算法:
實質:遞歸求解
缺點:如果子問題不獨立,需要重復求公共子問題
---------------------------------------------------------------------------------------------------------------------------
貪心算法:貪心算法采用的是逐步構造最優解的方法。在每個階段,都在一定的標准下做出一個看上去最優的決策。決策一旦做出,就不可能再更改。做出這個局部最優決策所依照的標准稱為貪心准則。
分治算法:分治法的思想是將一個難以直接解決大的問題分解成容易求解的子問題,以便各個擊破、分而治之。
動態規划:將待求解的問題分解為若干個子問題,按順序求解子階段,前一子問題的解,為后一子問題的求解提供了有用的信息。在求解任一子問題時,列出各種可能的局部解,通過決策保留那些有可能達到最優的局部解,丟棄其他局部解。依次解決各子問題,最后一個子問題就是初始問題的解。
二、算法間的關聯與不同
1、分治算法與動態規划
分治法所能解決的問題一般具有以下幾個特征:
① 該問題的規模縮小到一定程度就可以容易地解決。
② 該問題可以分為若干個較小規模的相似的問題,即該問題具有最優子結構性質。
③ 利用該問題分解出的子問題的解可以合並為該問題的解。
④ 該問題所分解出的各個子問題是相互獨立的且子問題即之間不包含公共的子問題。
上述的第一條特征是絕大多數問題都可以滿足的,因為問題的計算復雜性一般是隨着問題規模的增加而增加;
第二條特征是分治法應用的前提,它也是大多數問題可以滿足的,此特征反映了遞歸思想的應用;
第三條特征是關鍵,能否利用分治法完全取決於問題是否具有第三條特征,如果具備了第一條和第二條特征,而不具備第三條特征,則可以考慮貪心算法或動態規划算法;
第四條特征涉及到分治法的效率,如果各個子問題不是獨立的,則分治法要做許多不必要的工作,重復地解公共的子問題。這類問題雖然可以用分治法解決,但用動態規划算法解決效率更高。
當問題滿足第一、二、三條,而不滿足第四條時,一般可以用動態規划法解決,可以說,動態規划法的實質是: 分治算法思想+解決子問題冗余情況
2、貪心算法與動態規划算法
多階段逐步解決問題的策略就是按一定順序或一定的策略逐步解決問題的方法。分解的算法策略也是多階段逐步解決問題策略的一種表現形式,主要是通過對問題逐步分解,然后又逐步合並解決問題的。
貪心算法每一步都根據策略得到一個結果,並傳遞到下一步,自頂向下,一步一步地做出貪心決策。
動態規划算法的每一步決策給出的不是唯一結果,而是一組中間結果,而且這些結果在以后各步可能得到多次引用,只是每走一步使問題的規模逐步縮小,最終得到問題的一個結果。
舉例:如圖1有一三角形數塔,求一自塔頂到塔底的路徑,要求該路徑上結點的值的和最大。
貪心算法解題過程:自頂向下從第一層9開始,到第二層,選數值較大的15,第三層,在可選路徑中選數值較大的8,同理,第四層選9,第五層選10,這樣就確定了一條路徑:9→15→8→9→10。
動態規划算法接題過程:如圖2,階段1:自第五層開始,對經過第四層的2的路徑,在第五層的19、7中選擇數值較大的19,同理,對經過第四層18的路徑,選10,對經過第四層9的路徑,選10,對經過5的路徑選16。
以上是一次決策過程,也是一次遞推過程和降階過程。因為以上的決策結果將5階數塔問題變為4階子問題,遞推出第四層與第五層和為:
21(2+19),28(18+10),19(9+10),21(5+16)
用同樣的方法還可以將4階數塔問題變為3階數塔問題,……,最后得到1階數塔問題,這樣也確定了一條路徑:9→12→10→18→10,就是真個問題的最優解。
顯然,以上數塔問題用貪心算法得不到最優解,這里只是用作與動態規划算法的比較。
三、適用條件
貪心算法:
①貪心選擇性質:在求解一個問題的過程中,如果再每一個階段的選擇都是當前狀態下的最優選擇,即局部最優選擇,並且最終能夠求得問題的整體最優解,那么說明這個問題可以通過貪心選擇來求解,這時就說明此問題具有貪心選擇性質。
②最優子結構性質:當一個問題的最優解包含了這個問題的子問題的最優解時,就說明該問題具有最優子結構。
分治算法:見二、算法間的關聯與不同中的①②③④。
動態規划:
①最優化原理:如果問題的最優解所包含的子問題的解也是最優的,就稱該問題具有最優子結構,即滿足最優化原理。
②無后效性:即某階段狀態一旦確定,就不受這個狀態以后決策的影響。也就是說,某狀態以后的過程不會影響以前的狀態,只與當前狀態有關。
③有重迭子問題:即子問題之間是不獨立的,一個子問題在下一階段決策中可能被多次使用到。
四、優勢:
采用動態規划方法,可以高效地解決許多用貪婪算法或分而治之算法無法解決的問題。
但貪心算法也有它的優勢:構造貪心策略不是很困難,而且貪心策略一旦經過證明成立后,它就是一種高效的算法。