贪心与动态规划一.ppt

上传人:牧羊曲112 文档编号:6377288 上传时间:2023-10-22 格式:PPT 页数:51 大小:521KB
返回 下载 相关 举报
贪心与动态规划一.ppt_第1页
第1页 / 共51页
贪心与动态规划一.ppt_第2页
第2页 / 共51页
贪心与动态规划一.ppt_第3页
第3页 / 共51页
贪心与动态规划一.ppt_第4页
第4页 / 共51页
贪心与动态规划一.ppt_第5页
第5页 / 共51页
点击查看更多>>
资源描述

《贪心与动态规划一.ppt》由会员分享,可在线阅读,更多相关《贪心与动态规划一.ppt(51页珍藏版)》请在三一办公上搜索。

1、第十讲,贪心与动态规划(一),ACM算法与程序设计,数学科学学院:汪小平,导引问题:FatMouse Trade,Problem Description FatMouse prepared M pounds of cat food,ready to trade with the cats guarding the warehouse containing his favorite food,JavaBean.The warehouse has N rooms.The i-th room contains Ji pounds of JavaBeans and requires Fi pounds

2、 of cat food.FatMouse does not have to trade for all the JavaBeans in the room,instead,he may get Ji*a%pounds of JavaBeans if he pays Fi*a%pounds of cat food.Here a is a real number.Now he is assigning this homework to you:tell him the maximum amount of JavaBeans he can obtain.,Input The input consi

3、sts of multiple test cases.Each test case begins with a line containing two non-negative integers M and N.Then N lines follow,each contains two non-negative integers Ji and Fi respectively.The last test case is followed by two-1s.Output For each test case,print in a single line a real number accurat

4、e up to 3 decimal places,which is the maximum amount of JavaBeans that FatMouse can obtain.,Sample Input5 3 7 2 4 3 5 2-1-1Sample Output13.333,所谓“贪心算法”是指:,在对问题求解时,总是作出在当前看来是最好的选择。也就是说,不从整体上加以考虑,它所作出的仅仅是在某种意义上的局部最优解(是否是全局最优,需要证明)。,当一个问题的最优解包含着它的子问题的最优解时,称此问题具有最优子结构性质。当一个问题具有最优子结构性质时,我们会想到用动态规划法去解它。但有

5、时会有更简单有效的算法。顾名思义,贪心算法总是作出在当前看来是最好的选择。也就是说贪心算法并不从整体最优上加以考虑,它所作出的选择只是在某种意义上的局部最优选择。用贪心算法更简单,更直接且解题效率更高。虽然贪心算法不是对所有问题都能得到整体最优解,但对范围相当广的许多问题它能产生整体最优解。如图的单源最短路径问题,最小生成树问题等。在一些情况下,即使贪心算法不能得到整体最优解,但其最终结果却是最优解的很好的近似解。,特别说明:,若要用贪心算法求解某问题的整体最优解,必须首先证明贪心思想在该问题的应用结果就是最优解!,Moving Tables http:/,Description The fa

6、mous ACM(Advanced Computer Maker)Company has rented a floor of a building whose shape is in the following figure.,The floor has 200 rooms each on the north side and south side along the corridor.Recently the Company made a plan to reform its system.The reform includes moving a lot of tables between

7、rooms.Because the corridor is narrow and all the tables are big,only one table can pass through the corridor.Some plan is needed to make the moving efficient.The manager figured out the following plan:Moving a table from a room to another room can be done within 10 minutes.When moving a table from r

8、oom i to room j,the part of the corridor between the front of room i and the front of room j is used.So,during each 10 minutes,several moving between two rooms not sharing the same part of the corridor will be done simultaneously.To make it clear the manager illustrated the possible cases and imposs

9、ible cases of simultaneous moving.,Input The input consists of T test cases.The number of test cases)(T is given in the first line of the input.Each test case begins with a line containing an integer N,1=N=200,that represents the number of tables to move.Each of the following N lines contains two po

10、sitive integers s and t,representing that a table is to move from room number s to room number t(each room number appears at most once in the N lines).From the N+3-rd line,the remaining test cases are listed in the same manner as above.Output The output should contain the minimum time in minutes to

11、complete the moving,one per line.,Sample Input 3 4 10 20 30 40 50 60 70 80 2 1 3 2 200 3 10 100 20 80 30 50 Sample Output 10 20 30,算法分析:,1、如果没有交叉,总时间应该是多少?2、影响搬运时间的因素是什么?3、如果每趟处理都包含最大重叠,处理后的效果是什么?4、得出什么结论?,#include using namespace std;int main()int t,i,j,N,P200;int s,d,temp,k,min;scanf(%d,if(sd)temp

12、=s;s=d;d=temp;for(k=s;kmin)min=Pj;printf(%dn,min*10);return 0;,贪心算法的基本步骤,1、从问题的某个初始解出发。2、采用循环语句,当可以向求解目标前进一步时,就根据局部最优策略,得到一个部分解,缩小问题的范围或规模。3、将所有部分解综合起来,得到问题的最终解。,贪心算法都很简单吗?,看一道难一些的。(2004年上海赛区:正式赛是简单题),ACM-ICPC Asia Regional,2004,Shanghai,Tian JiThe Horse Racing,Problem Description Here is a famous s

13、tory in Chinese history.That was about 2300 years ago.General Tian Ji was a high official in the country Qi.He likes to play horse racing with the king and others.Both of Tian and the king have three horses in different classes,namely,regular,plus,and super.The rule is to have three rounds in a matc

14、h;each of the horses must be used in one round.The winner of a single round takes two hundred silver dollars from the loser.“Being the most powerful man in the country,the king has so nice horses that in each class his horse is better than Tians.As a result,each time the king takes six hundred silve

15、r dollars from Tian.Tian Ji was not happy about that,until he met Sun Bin,one of the most famous generals in Chinese history.Using a little trick due to Sun,Tian Ji brought home two hundred silver dollars and such a grace in the next match.It was a rather simple trick.Using his regular class horse r

16、ace against the super class from the king,they will certainly lose that round.But then his plus beat the kings regular,and his super beat the kings plus.What a simple trick.And how do you think of Tian Ji,the high ranked official in China?,Were Tian Ji lives in nowadays,he will certainly laugh at hi

17、mself.Even more,were he sitting in the ACM contest right now,he may discover that the horse racing problem can be simply viewed as finding the maximum matching in a bipartite graph.Draw Tians horses on one side,and the kings horses on the other.Whenever one of Tians horses can beat one from the king

18、,we draw an edge between them,meaning we wish to establish this pair.Then,the problem of winning as many rounds as possible is just to find the maximum matching in this graph.If there are ties,the problem becomes more complicated,he needs to assign weights 0,1,or-1 to all the possible edges,and find

19、 a maximum weighted perfect matching.However,the horse racing problem is a very special case of bipartite matching.The graph is decided by the speed of the horses-a vertex of higher speed always beat a vertex of lower speed.In this case,the weighted bipartite matching algorithm is a too advanced too

20、l to deal with the problem.In this problem,you are asked to write a program to solve this special case of matching problem.,示意图:,InputThe input consists of up to 50 test cases.Each case starts with a positive integer n(n=1000)on the first line,which is the number of horses on each side.The next n in

21、tegers on the second line are the speeds of Tians horses.Then the next n integers on the third line are the speeds of the kings horses.The input ends with a line that has a single 0 after the last test case.OutputFor each input case,output a line containing a single number,which is the maximum money

22、 Tian Ji will get,in silver dollars.,Sample Input3 92 83 71 95 87 74 2 20 20 20 20 2 20 19 22 18 0Sample Output200 0 0,谈谈自己的想法吧,Case 1:,King:200 180 160Tianji:190 170 150,Case 2:,King:200 180 160Tianji:180 170 150,Case 3:,King:200 180 160Tianji:180 155 150,总体的思路是什么?,1 对田忌和王的马的速度按从大到小排序2.1如果田忌最慢的马比大王

23、最慢的马快 那么先赢一局2.2如果田忌最慢的马比大王最慢的马慢 那么用最慢的马和大王最快的马比赛2.3如果田忌最慢的马和大王最慢的马的速度一样 分情况讨论贪心 2.3.1如果田忌当前最快的马比大王当前最快的马速度还要快就直接比掉2.3.2如果田忌当前最快的马比大王当前最快的马速度慢,田忌拿当前最慢的马和大王当前最快的马比2.3.3如果田忌当前最快的马和大王当前最快的马的速度一样,田忌就选取一匹最慢的马和大王最快的马比,此时不用考虑田忌最慢的马的速度和大王最快马的速度一样,提醒:,很多贪心类型的题目都象本题一样,不是最朴素的贪心,而是需要做一些变化,对于我们,关键是找到贪心的本质!,贪心算法与简

24、单枚举和动态规划的运行方式比较,贪心算法一般是求“最优解”这类问题最优解问题可描述为:有 n 个输入,它的解是由这 n 个输入的某个子集组成,并且这个子集必须满足事先给定的条件。这个条件称为约束条件。而把满足约束条件的子集称为该问题的可行解。这 些可行解可能有多个。为了衡量可行解的优劣,事先给了一个关于可行解的函数,称为目标函数。目标函数最大(或最小)的可行解,称为最优解。,求“最优解”最原始的方法为搜索枚举方案法(一般为回溯法)。一般用深度优先搜索或宽度优先搜索。现今竞赛中用的比较普遍的动态规划,主要是利用最优子问题的确定性,从后向前(即从小规模向大规模)得到当前最优策略,从而避免了重复的搜

25、索。,动态规划要满足最优子结构原则,贪心算法呢?可以认为贪心算法的正确性证明是个难点。,NOI 中的“石子合并”一题:在一个圆形操场的四周摆放 N 堆石子(N100),现要将石子有次序地合并 成一堆。规定每次只能选相邻的两堆合并成新的一堆,并将新的一堆的石子数,记为该次合并的得分。选择一种合并石子的方案,使得做 N-1 次合并,得分的总和最小;选择一种合并石子的方案,使得做 N-1 次合并,得分的总和最大。,贪心算法的最小值为:(2+3)=5(4+5)=9(4+5)=9(9+6)=15(15+9)=245+9+9+15+2462 另一种方法的最小值为:(2+4)=6(3+4)=7(5+6)=1

26、1(7+6)=13(11+13)=246+7+11+13+2461,在一个mn棋盘内(m,n均不超过100),每个格子内有一个正整数值(不超过100)表示占据该格子应支付的费用。一个国际象棋的武士从棋盘左下角格子(1,1)开始沿着向右或向上的方向向右上角格子(m,n)行进,要求找一条行进路径使武士支付的费用最小。d(i,j)=w(i,j)+min(d(i-1,j),d(i,j-1),1、找出最优解的性质,并刻画其结构特征;2、递归地定义最优值(写出动态规划方程);3、以自底向上的方式计算出最优值;4、根据计算最优值时得到的信息,构造一个最优解。以上就是动态规划算法的基本步骤,动态规划的基本思想

27、:动态规划算法通常用于求解具有某种最优性质的问题。在这类问题中,可能会有许多可行解。每一个解都对应于一个值,我们希望找到具有最优值的解。动态规划算法与分治法类似,其基本思想也是将待求解问题分解成若干个子问题,先求解子问题,然后从这些子问题的解得到原问题的解。与分治法不同的是,适合于用动态规划求解的问题,经分解得到子问题往往不是互相独立的。若用分治法来解这类问题,则分解得到的子问题数目太多,有些子问题被重复计算了很多次。如果我们能够保存已解决的子问题的答案,而在需要时再找出已求得的答案,这样就可以避免大量的重复计算,节省时间。我们可以用一个表来记录所有已解的子问题的答案。不管该子问题以后是否被用

28、到,只要它被计算过,就将其结果填入表中。这就是动态规划法的基本思路。具体的动态规划算法多种多样,但它们具有相同的填表格式。,动态规划问题中的术语,最优化原理:无论过去的状态和决策如何,对前面的决策所形成的状态而言,余下的诸决策必须构成最优策略的性质。也可以通俗地理解为子问题的局部最优将导致整个问题的全局最优,即问题具有最优子结构的性质,也就是说一个问题的最优解只取决于其子问题的最优解,而非最优解对问题的求解没有影响。无后效性原则:某阶段的状态一旦确定,则此后过程的演变不再受此前各状态及决策的影响。也就是说,“未来与过去无关”,当前的状态是此前历史的一个完整的总结,此前的历史只能通过当前的状态去

29、影响过程未来的演变。够采用动态规划方法求解的问题,必须满足最优化原理和无后效性原则,数字三角形,1、问题描述,上图给出了一个数字三角形。从三角形的顶部到底部有很多条不同的路径。对于每条路径,把路径上面的数加起来可以得到一个和,和最大的路径称为最佳路径。你的任务就是求出最佳路径上的数字之和。注意:路径上的每一步只能从一个数走到下一层上和它最近的左边的数或者右边的数。,输入数据输入的第一行是一个整数N(1 N=100),给出三角形的行数。下面的N 行给出数字三角形。数字三角形上的数的范围都在0 和100 之间。输出要求输出最大的和。,输入样例573 88 1 02 7 4 44 5 2 6 5输出

30、样例30,2、解题思路,这道题目可以用递归的方法解决。基本思路是:以D(r,j)表示第r 行第 j 个数字(r,j 都从1 开始算),以MaxSum(r,j)代表从第 r 行的第 j 个数字到底边的最佳路径的数字之和,则本题是要求 MaxSum(1,1)。从某个D(r,j)出发,显然下一步只能走D(r+1,j)或者D(r+1,j+1)。如果走D(r+1,j),那么得到的MaxSum(r,j)就是MaxSum(r+1,j)+D(r,j);如果走D(r+1,j+1),那么得到的MaxSum(r,j)就是MaxSum(r+1,j+1)+D(r,j)。所以,选择往哪里走,就看MaxSum(r+1,j)

31、和MaxSum(r+1,j+1)哪个更大了。,3、参考程序 I,#include#define MAX_NUM 100int DMAX_NUM+10MAX_NUM+10;int N;int MaxSum(int r,int j)if(r=N)return Drj;int nSum1=MaxSum(r+1,j);int nSum2=MaxSum(r+1,j+1);if(nSum1 nSum2)return nSum1+Drj;return nSum2+Drj;,int main(void)int m;scanf(%d,提交结果:Time Limit Exceed,程序I分析,上面的程序,效率非常

32、低,在N 值并不大,比如N=100 的时候,就慢得几乎永远算不出结果了。为什么会这样呢?是因为过多的重复计算。我们不妨将对MaxSum 函数的一次调用称为一次计算。那么,每次计算MaxSum(r,j)的时候,都要计算一次MaxSum(r+1,j+1),而每次计算MaxSum(r,j+1)的时候,也要计算一次MaxSum(r+1,j+1)。重复计算因此产生。在题目中给出的例子里,如果我们将MaxSum(r,j)被计算的次数都写在位置(r,j),那么就能得到右面的三角形:,11 11 2 11 3 3 11 4 6 4 1,73 88 1 02 7 4 44 5 2 6 5,程序分析,从上图可以看

33、出,最后一行的计算次数总和是16,倒数第二行的计算次数总和是8。不难总结出规律,对于N 行的三角形,总的计算次数是20+21+22+2(N-1)=2N-1。当N=100 时,总的计算次数是一个让人无法接受的大数字。既然问题出在重复计算,那么解决的办法,当然就是,一个值一旦算出来,就要记住,以后不必重新计算。即第一次算出MaxSum(r,j)的值时,就将该值存放起来,下次再需要计算MaxSum(r,j)时,直接取用存好的值即可,不必再次调用MaxSum 进行函数递归计算了。这样,每个MaxSum(r,j)都只需要计算1 次即可,那么总的计算次数(即调用MaxSum 函数的次数)就是三角形中的数字

34、总数,即1+2+3+N=N(N+1)/2。如何存放计算出来的MaxSum(r,j)值呢?显然,用一个二维数组aMaxSumNN就能解决。aMaxSumrj就存放MaxSum(r,j)的计算结果。下次再需要MaxSum(r,j)的值时,不必再调用MaxSum 函数,只需直接取aMaxSumrj的值即可。,4、参考程序 II,#include#include#define MAX_NUM 100int DMAX_NUM+10MAX_NUM+10;int N;int aMaxSumMAX_NUM+10MAX_NUM+10;int MaxSum(int r,int j)if(r=N)return Dr

35、j;if(aMaxSumr+1j=-1)/如果MaxSum(r+1,j)没有计算过 aMaxSumr+1j=MaxSum(r+1,j);if(aMaxSumr+1j+1=-1)aMaxSumr+1j+1=MaxSum(r+1,j+1);if(aMaxSumr+1j aMaxSumr+1j+1)return aMaxSumr+1j+Drj;return aMaxSumr+1j+1+Drj;,int main(void)int m;scanf(%d,程序II分析,以上题为例,最佳路径上面的每个数字到底部的那一段路径,都是从该数字出发到达到底部的最佳路径。实际上,递归的思想在编程时未必要实现为递归函

36、数。在上面的例子里,有递推公式:,因此,不需要写递归函数,从aMaxSumN-1这一行元素开始向上逐行递推,就能求得aMaxSum11的值了。,5、参考程序 III,int DMAX_NUM+10MAX_NUM+10;int N;int aMaxSumMAX_NUM+10MAX_NUM+10;int main(void)int i,j;scanf(%d,思考题:上面的几个程序只算出了最佳路径的数字之和。如果要求输出最佳路径上的每个数字,该怎么办?,动态规划解题的一般思路,许多求最优解的问题可以用动态规划来解决。首先要把原问题分解为若干个子问题。注意单纯的递归往往会导致子问题被重复计算,用动态规

37、划的方法,子问题的解一旦求出就要被保存,所以每个子问题只需求解一次。子问题经常和原问题形式相似,有时甚至完全一样,只不过规模从原来的n 变成了n-1,或从原来的nm 变成了n(m-1)等等。找到子问题,就意味着找到了将整个问题逐渐分解的办法。分解下去,直到最底层规模最小的的子问题可以一目了然地看出解。每一层子问题的解决,会导致上一层子问题的解决,逐层向上,就会导致最终整个问题的解决。如果从最底层的子问题开始,自底向上地推导出一个个子问题的解,那么编程的时候就不需要写递归函数。,用动态规划解题时,将和子问题相关的各个变量的一组取值,称之为一个“状态”。一个“状态”对应于一个或多个子问题,所谓某个

38、“状态”下的“值”,就是这个“状态”所对应的子问题的解。比如数字三角形,子问题就是“从位于(r,j)数字开始,到底边路径的最大和”。这个子问题和两个变量r 和j 相关,那么一个“状态”,就是r,j 的一组取值,即每个数字的位置就是一个“状态”。该“状态”所对应的“值”,就是从该位置的数字开始,到底边的最佳路径上的数字之和。定义出什么是“状态”,以及在该“状态”下的“值”后,就要找出不同的状态之间如何迁移即如何从一个或多个“值”已知的“状态”,求出另一个“状态”的“值”。状态的迁移可以用递推公式表示,此递推公式也可被称作“状态转移方程”。,用动态规划解题,如何寻找“子问题”,定义“状态”,“状态转移方程”是什么样的,并没有一定之规,需要具体问题具体分析,题目做多了就会有感觉。甚至,对于同一个问题,分解成子问题的办法可能不止一种,因而“状态”也可以有不同的定义方法。不同的“状态”定义方法可能会导致时间、空间效率上的区别。,

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 生活休闲 > 在线阅读


备案号:宁ICP备20000045号-2

经营许可证:宁B2-20210002

宁公网安备 64010402000987号