1、贪心算法技巧.ppt

贪心算法 问题引入: 有下面几种面值的硬币:一元、五角、一角、五分、一分,假设要付给顾客2.89元的零钱,要求用最少的硬币。 顾名思义,贪心算法总是作出在当前看来最好的选择。也就是说贪心算法并不从整体最优考虑,它所作出的选择只是在某种意义上的局部最优选择。当然,希望贪心算法得到的最终结果也是整体最优的。虽然贪心算法不能对所有问题都得到整体最优解,但对许多问题它能产生整体最优解。如单源最短路经问题,最小生成树问题等。在一些情况下,即使贪心算法不能得到整体最优解,其最终结果却是最优解的很好近似。 主要知识点: 活动安排问题 背包问题 最优装载 单源最短路径 最小生成树 活动安排问题 活动安排问题就是要在所给的活动集合中选出最大的相容活动子集合,是可以用贪心算法有效求解的很好例子。该问题要求高效地安排一系列争用某一公共资源的活动。贪心算法提供了一个简单、漂亮的方法使得尽可能多的活动能兼容地使用公共资源。 活动安排问题 活动安排问题 在下面所给出的解活动安排问题的贪心算法greedySelector : int greedySelector(int s[], int f[], boolean a[]) { int n=s.length-1; a[1]=true; int j=1; int count=1; for (int i=2;i=n;i++) { if (s[i]=f[j]) { a[i]=true; j=i; count++; } else a[i]=false; } return count; } 活动安排问题 例:设待安排的11个活动的开始时间和结束时间按结束时间的非减序排列如下: 活动安排问题 若被检查的活动i的开始时间Si小于最近选择的活动j的结束时间fi,则不选择活动i,否则选择活动i加入集合A中。 贪心算法并不总能求得问题的整体最优解。但对于活动安排问题,贪心算法greedySelector却总能求得的整体最优解,即它最终所确定的相容活动集合A的规模最大。这个结论可以用数学归纳法证明。 背包问题 给定n种物品和一个背包。物品i的重量是Wi,其价值为Vi,背包的容量为C。应如何选择装入背包的物品,使得装入背包中物品的总价值最大?(假定物品可以分割成更小部分,亦即物品可以部分装入) 用贪心算法解背包问题的基本步骤: 首先计算每种物品单位重量的价值Vi/Wi,然后,依贪心选择策略,将尽可能多的单位重量价值最高的物品装入背包。若将这种物品全部装入背包后,背包内的物品总重量未超过C,则选择单位重量价值次高的物品并尽可能多地装入背包。依此策略一直地进行下去,直到背包装满为止。 具体算法可描述如下页: float knapsack(float c,float w[], float v[],float x[]) { int n=v.length; for (int i = 0; i n; i++) d[i] = (w[i],v[i],i); MergeSort.mergeSort(d); int i; float opt=0; for (i=0;in;i++) x[i]=0; for (i=0;in;i++) { if (d[i].wc) break; x[d[i].i]=1; opt+=d[i].v; c-=d[i].w; } if (in){ x[d[i].i]=c/d[i].w; opt+=x[d[i].i]*d[i].v; } return opt; } 最优装载 有一批集装箱要装上一艘载重量为c的轮船。其中集装箱i的重量为Wi。最优装载问题要求确定在装载体积不受限制的情况下,将尽可能多的集装箱装上轮船。 1.算法描述 最优装载问题可用贪心算法求解。采用重量最轻者先装的贪心选择策略,可产生最优装载问题的最优解。具体算法描述如下页。 float loading(float c, float [] w, int [] x) { int n=w.length; for (int i = 0; i n; i++) d[i

文档评论(0)

1亿VIP精品文档

相关文档