概念:
當一個問題具有最優子結構性質時,可用動態規划算法,有時會有更簡單有效的算法,那就是貪心算法,貪心算法是通過一系列的選擇來得到問題的解,貪心算法並不從整體最優上加以考慮,所做的選擇只是在某種意義上的局部最優解。但對范圍相當廣的許多問題能產生整體最優解。在一些情況下,即使貪心算法不能得到整體最優解,但其最終結果卻是最優解的很好的近似解。
貪心算法的基本要素:
貪心選擇性質:所求解的問題的整體最優解可以通過一系列局部最優的選擇來,即貪心選擇達到。貪心選擇所依賴的是以前所做過的選擇,而對以后所做的選擇沒有關系。
最優子結構性質:一個問題的最優解包含其子問題的最優解。
貪心算法與動態規划的區別:
動態規划是通過自底向上的方式解決子問題,貪心算法是通過自頂向下的迭代方式做出貪心選擇,求解問題的最優解。兩共同點是都具有最優子結構性質。
最優裝載問題:某艘船的載重量為C,每件物品的重量為wi,要將盡量多的物品裝入到船上。
分析:貪心策略:每次都選擇最輕的,然后再從剩下的n-1件物品中選擇最輕的。
算法策略:把n件物品 從小到大排序,然后根據貪心策略盡可能多的選出前i個物品,直到不能裝為止。
這個問題比部分背包問題還簡單,先拿輕的再拿重的可以保證最后物品裝的最多。代碼如下:

#include<iostream> #include<algorithm> #define MAXN 10000 using namespace std; int main(){ int c,n; //c:船的最高載重量 n:古董數量 int sum=0,weight=0; //sum:裝入的古董數量 weight:裝入的古董重量 int w[MAXN]; //單個古董對應的重量 cout<<"請輸入最高載重量和需載的古董數目:"<<endl; cin>>c>>n; cout<<"請分別輸入這些古董的重量:"<<endl; for(int i=1;i<=n;++i) cin>>w[i]; sort(w+1,w+1+n); for(int i = 1 ; i<=n ; i++){ weight += w[i]; //先將重量加進去 if(weight >= c){ if(weight == c) //恰好裝滿時 sum = i; else sum = i-1; //超重了,需要減去一個 break; } } cout<<"最多可以裝"<<sum<<"個"<<endl; for(int i=1;i<=sum;++i) cout<<w[i]<<" "; return 0; }
程序運行結果:
參考:王曉東《算法設計與分析》