貪心基礎css
貪心(Greedy)經常使用於解決最優問題,以期經過某種策略得到一系列局部最優解、從而求得總體最優解。html
貪心從局部最優角度考慮,只適用於具有無後效性的問題,即某個狀態之前的過程不影響之後的狀態、緊接下來的狀態僅與當前狀態有關。和分治、動態規劃同樣,貪心是一種思路,不是解決某類問題的具體方法。git
應用貪心的關鍵,是甄別問題是否具有無後效性、找到得到局部最優的策略。有的問題比較淺顯,例如一道找零錢的題目 LeetCode 860. Lemonade Change:github
// 860. Lemonade Change bool lemonadeChange(vector<int>& bills) { int five=0,ten=0; for(auto i:bills){ if(i==5) five++; else if(i==10) ten++,five--; else if(ten>0) ten--,five--; else five-=3; if(five<0) return false; } return true; }
以上策略的核心就是每輪找零用最大的面額、保留儘可能多5元紙幣。算法
相關LeetCode題:cookie
122. Best Time to Buy and Sell Stock II 題解app
1090. Largest Values From Labels 題解spa
984. String Without AAA or BBB 題解
但一些問題不那麼直觀,須要深一層考慮局部最優的策略,例如 LeetCode題目 55. Jump Game:
// 55. Jump Game bool canJump(vector<int>& nums) { int res=0; for(int i=0;i<=res;i++){ res=max(res,i+nums[i]); if(res>=nums.size()-1) return true; } return false; }
以上每輪更新最遠能夠到達的位置。
相關LeetCode題:
861. Score After Flipping Matrix 題解
921. Minimum Add to Make Parentheses Valid 題解
1053. Previous Permutation With One Swap 題解
貪心與優先級隊列
一些貪心策略是每輪獲取極值處理,這時能夠藉助於優先級隊列,關於優先級隊列詳見:
算法與數據結構基礎 - 堆(Heap)和優先級隊列(Priority Queue)
相關LeetCode題:
1005. Maximize Sum Of Array After K Negations 題解
1167. Minimum Cost to Connect Sticks 題解
358. Rearrange String k Distance Apart 題解
貪心與排序
相似地,也能夠經過排序得到極值以用於貪心策略,關於排序詳見:
相關LeetCode題:
406. Queue Reconstruction by Height 題解
452. Minimum Number of Arrows to Burst Balloons 題解
435. Non-overlapping Intervals 題解
優先級隊列和排序還能夠一塊兒應用於貪心策略(這類貪心策略我稱之爲多層貪心策略),例如針對二維數據,先對第一維排序、而後經過優先級隊列對第二維取極值。
原文出處:https://www.cnblogs.com/bangerlee/p/11416605.html