第4讲 构造法.ppt

  1. 1、本文档共152页,可阅读全部内容。
  2. 2、原创力文档(book118)网站文档一经付费(服务费),不意味着购买了该文档的版权,仅供个人/单位学习、研究之用,不得用于商业用途,未经授权,严禁复制、发行、汇编、翻译或者网络传播等,侵权必究。
  3. 3、本站所有内容均由合作方或网友上传,本站不对文档的完整性、权威性及其观点立场正确性做任何保证或承诺!文档内容仅供研究参考,付费前请自行鉴别。如您付费,意味着您自己接受本站规则且自行承担风险,本站不退款、不进行额外附加服务;查看《如何避免下载的几个坑》。如果您已付费下载过本站文档,您可以点击 这里二次下载
  4. 4、如文档侵犯商业秘密、侵犯著作权、侵犯人身权等,请点击“版权申诉”(推荐),也可以打举报电话:400-050-0827(电话支持时间:9:00-18:30)。
查看更多
第4讲 构造法

贪心法与构造法 一、贪心法 删数问题 键盘输入一个高精度的正整数N,去掉其中任意S个数字后剩下的数字按原左右次序将组成一个新的正整数。编程对给定的N和S,寻找一种方案使得剩下的数字组成的新数最小。 输出应包括所去掉的数字的位置和组成的新的正整数。(N不超过240位) 输入数据均不需判错。 ? 试题中正整数N 的有效位数为240位,必须采用可含256个字符的字串来替代整数。 贪心选择:使用尽可能逼尽目标的方法来逐一删去其中S个数符,每一步总是选择一个使剩下的数最小的数符删去。具体: 按低位→高位的方向搜索递增区间。若不存在递增区间,则删尾数符;否则删递增区间的尾字符,这样形成了一个新数串。然后回到串尾,重复上述规则,删下一数符……依此类推,直至删除S个数符为止。 例如:N=178543,S=4,删数过程如下: ↓ N=1 7 8 5 4 3 ↓ 1 7 5 4 3 ↓ 1 5 4 3 ↓ 1 4 3 1 3 write(‘N=’); readln(N); {输入数串} write(‘S=’); readln(S); {输入应删的数字个数} while S0 do begin {逐一删去S个数符} i:=1; while (ilength(N)) and (N[i]=N[i+1]) do inc(i);{搜索递增区间} delete(N,i,1); {删去该区间的首数符} dec(S); end; {while} while(length(N)1)and(N[1]=‘0’)do delete(N,1,1);{删去串头的无用零} writeln(N); {输出剩下的数码} 贪心法的特点 1.贪心选择性质──可通过做局部最优(贪心)选择来达到全局最优解 贪心策略通常是自顶向下做的。第一步为一个贪心选择,将原问题变成一个相似的、但规模更小的问题,而后的每一步都是当前看似最佳的选择。这种选择可能依赖于已作出的所有选择,但不依赖有待于做的选择或子问题的解。从求解的全过程来看,每一次贪心选择都将当前问题归纳为更小的相似子问题,而每一个选择都仅做一次,无重复回溯过程,因此贪心法有较高的时间效率。 2.最优子结构──问题的最优解包含了子问题的最优解。 背包问题 有一个贼在偷窃一家商店时发现有N件物品:第i件物品值Vi 元,重Wi 磅,(1≤i≤n),此处Vi 和Wi 都是整数。他希望带走的东西越值钱越好,但他的背包中最多只能装下W磅的东西(W为整数)。有两种偷窃方式: 1.01──背包问题 如果每件物品或被带走或被留下,小偷应该带走哪几件东西? 2.部分背包问题 如果允许小偷可带走某个物品的一部分,小偷应该带走哪几件东西,每件东西的重量是多少? 采用贪心策略来解决部分背包问题: 先对每件物品计算其每磅价值Vi /Wi ,然后按每磅价值单调递减的顺序对所有物品排序。例如,总共有三件物品和一个背包 ? ? ? ? ? ? ? ? 按照一种贪心策略,窃贼开始时对具有最大的每磅价值的物品尽量多拿一些。如果他拿完了该物品后仍可以取一些其他物品时,他就再取具有次大的每磅价值的物品,一直继续下去,直到不能取为止 ? ? ? ? ? 设List为物件序列,其中list[I].k, list[I].w, list[I].v, list[I]. pper为物件I的编号、重量、价值和每磅价值 Readln(F, N, W);读入物件数n和背包容量w; For i := 1 to N Do Begin 读物件i的重量List[i].w和价值List[i].v, List[i].vper := List[i].v / List[i].w List[i].k := i;{计算其每磅价值并记下编号} End;{for} 对List 按每磅价值递减的顺序进行排序; V := 0; i := 1; Writeln(‘Num’:5, ‘Weight’:9, ‘Value’:8);{打印表目} While W List[i].w Do Begin{依次取走当前最值钱的物件,并累计窃走物件的价值和} W := W - List[i].w; V := v + Li

文档评论(0)

gz2018gz + 关注
实名认证
内容提供者

该用户很懒,什么也没介绍

1亿VIP精品文档

相关文档