贪心算法--就是一种寻找局部最优解的情况,然后整合成整体最优解的情况

简单的例子:买菜的找钱,现在有1元,5角,1角的硬币,要找给别人2元7角,现在是怎么才能以最少的硬币量找给别人,肯定是先来两个1元的,再来1个5角的,最后两个1角的,但是,这个是我们一眼就能想到的,如何将它抽象成算法的思想呢?

第一步:先找到面值不超过2元7角的最大的硬币,只有1元,还剩下1元7角

第二步:再找到面值不超过1元7角的最大的硬币,只有1元,还剩下7角,

第三步,找到面值不超过7角的最大的硬币,有5角,还剩2角

第四步,找到面值不超过2角的最大的硬币,有1角,还剩1角

第五步,找到面值不超过1角的最大的硬币,有1角,还剩0角

第六步,找到面值不超过0角的最大的硬币,没有,结束

以上其实就是算法的思想,看似很简答,其实也是比较繁琐,最主要的就是找到当前下的最优的解,不管整体怎么样,思想也很简单,但是,什么时候去使用贪心算法,这点就很难了,要满足两个条件,能够找到当前的最优的解,其次最优子结构体是整体最优解的一部分,要使用贪心算法之前你得先要验证是不是可以来使用这个。。。这一点就比较鸡肋了,可是,不管怎么来说,最后能不能得到最优解,贪心算法都是执行效率很高的算法思想。

说了这么多,实践才是验证真理的唯一标准,那我们就来愉快的做个题吧。。。

package thinking;import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;import org.junit.Test;/* QUESTION : optimal loading problem* DESCRIBTION : Now we have some boxs need to be loaded into a ship which the limit of its load capacity is C ,and*                 every weight of box is designated by the user. The Volume(体积) of this ship isn't limit. So how can *                 we load boxes as many as possible? * * */
class Ship{private int capacity;public void setCapacity(int capacity) {this.capacity = capacity;}public int getCapacity() {return capacity;}
}class Box{private int weight;public void setWeight(int weight) {this.weight = weight;}public int getWeight() {return weight;}
}public class Greedy {Ship ship = new Ship();Box box1 = new Box();Box box2 = new Box();Box box3 = new Box();Box box4 = new Box();Box box5 = new Box();@Testpublic void lookingForTheBestChoise(){// step 1 : initialize the info of ship and boxesSystem.out.println("please input the capacity of ur ship!");Scanner scanner = new Scanner(System.in);int capacity = scanner.nextInt();ship.setCapacity(capacity);System.out.println("please input the werght of ur boxes(5)!");int b1 = scanner.nextInt();int b2 = scanner.nextInt();int b3 = scanner.nextInt();int b4 = scanner.nextInt();int b5 = scanner.nextInt();box1.setWeight(b1);box2.setWeight(b2);box3.setWeight(b3);box4.setWeight(b4);box5.setWeight(b5);List<Box> boxes = new ArrayList<Box>();boxes.add(box1);boxes.add(box2);boxes.add(box3);boxes.add(box4);boxes.add(box5);List<Box> sortedList = sort(boxes);// step 2 : looking for the best solution step by stepint index = 0;while(capacity != 0){if(sortedList.get(0).getWeight() > capacity){System.out.println("ur capacity of ship is too light!");System.exit(0);}else{if(sortedList.get(index).getWeight() < capacity){System.out.print(sortedList.get(index).getWeight());capacity = capacity-sortedList.get(index).getWeight();index++;}else{System.out.println("no more can be loaded");System.exit(0);}}}}List<Box> sort(List<Box> boxes){//List<Box> sortedList = new ArrayList<Box>();for(int i = 0; i<boxes.size(); ++i){for(int j = 0; j < boxes.size()-i-1; ++j){int tempWeight;if(boxes.get(j).getWeight() > boxes.get(j+1).getWeight()){tempWeight = boxes.get(j).getWeight();boxes.get(j).setWeight(boxes.get(j+1).getWeight()); boxes.get(j+1).setWeight(tempWeight);}}}for (Box box : boxes) {System.out.println(box.getWeight());}return boxes;}public static void main(String[] args) {//Scanner s = new Scanner(System.in);
        }
}

上面的问题很简单,透过现象看本质就是从小到大一个排序的过程,然后累加。。。还不能很好的体现出贪心的这种感觉,那我们就来一个经典一点的背包问题

package thinking;import java.util.Scanner;import org.junit.Test;/* QUESTION : A traveler has a backpack of up to Mkg, and now has n items, each weighing W1, W2,...Wn.The value of*               each piece are respectively C1, C2,...,Cn.the number of each item if enough. The maxinum value of a *               traveler.* */public class PackageQuestion {int capacity;int n; // 物件的数量
    @Testpublic void getMaxValue(){// 输入物件信息System.out.println("please input the capacity of backpack!");Scanner sca = new Scanner(System.in);capacity = sca.nextInt();System.out.println("please input the number of the items!");n = sca.nextInt();int[] weight = new int[n]; // 重量数组int[] value = new int[n];  // 对应的价值数组int[] index = new int[n];  // 一个额外的记录变化的数组,后面会进行排序交换,所以每一个物品都要贴一个标签System.out.println("please input the weight of these items!");for(int i = 0; i<n; ++i){weight[i] = sca.nextInt();}System.out.println("please input the value of these items!");for(int i =0; i<n; ++i){value[i] = sca.nextInt();}//下面就是重场戏了// 因为每个物品的重量和价值都不一样,直观可比性不强,所以我们想要一个可以直观比较的参数,进而想到单位重量下的价值double[] ev = new double[n]; // 单位重量下的价值数组for(int i = 0; i<n; ++i){double v = (double)value[i] / (double)weight[i];ev[i] = v;index[i] = i; //初始化标志
        }// 然后下面就是一个复杂的按照价值的由高到低的排序的过程,采用选择排序或者冒泡都可以。for(int i = 0; i<n-1; ++i){for(int j = i+1; j<n; ++j){if(ev[i] < ev[j]){// 前面的单位重量下的价值小于后面的,就交换位置double temp;temp = ev[i];ev[i] = ev[j];ev[j] = temp;// 位置的改变后,一定要注意标志位置的也要改变int temp3 = index[i];index[i] = index[j];index[j] = temp3;}}}// 用两个新数组来装这个排好序的重量和价值int[] wei = new int[n];int[] val = new int[n];for(int i = 0; i<n; ++i){wei[i] = weight[index[i]];val[i] = value[index[i]];}//排好序后的监测一下System.out.println("weight:");for(int i = 0; i<n; ++i){System.out.print(wei[i]+"\t");}System.out.println("value:");for(int i = 0; i<n; ++i){System.out.print(val[i]+"\t");}System.out.println("index:");for(int i = 0; i<n; ++i){System.out.print(index[i]+"\t");}//排好序后就开始进行贪心子结构最优化int x = 0;while(capacity > 0){if(wei[0] > capacity){System.out.println("ur backpack is too small, get changed!");System.exit(0);}else{if(wei[x] < capacity){System.out.println("get the value is "+val[x]+" item");capacity = capacity-wei[x];x++;}else{System.out.println("ur backpack can't pack any more!");System.exit(0);}}}}public static void main(String[] args) {}
}

上面这个稍微复杂一些,但还是逃脱不开从最值找的一个步骤,只不过这里的最值稍微做了一点技巧就是求了一个单位最值,从而来提高精准度,并且加上了标志数据的标志,思路也是比较简单的。

转载于:https://www.cnblogs.com/AmoryWang-JavaSunny/p/6504346.html

Arithmetic_Thinking -- greedy algorithm相关推荐

  1. 数据结构与算法(C++)– 贪婪算法(Greedy algorithm)

    贪婪算法(Greedy algorithm) 1.基础 定义:贪婪算法分阶段地工作,在每一阶段,选择在当前最好的决策,不考虑将来的后果.所以一般只能得到局部最优而不是全局最优. 贪婪算法: Dijks ...

  2. 动态规划(Dynamic Programming)与贪心算法(Greedy Algorithm)

    文章目录 动态规划算法(Dynamic Programming) 动态规划问题的属性 应用实例:最长公共子序列问题(Longest Common Subsequence, LCS) 贪心算法(Gree ...

  3. 贪心(Greedy Algorithm)

    贪心(Greedy Algorithm) 贪心 44.通配符匹配 45.跳跃游戏 II 55.跳跃游戏 122.买卖股票的最佳时机II 134.加油站 135.分发糖果 179.最大数 277.搜寻名 ...

  4. 贪婪算法-Greedy algorithm

    贪婪算法(greedy algorithm) WIKI A greedy algorithm is an algorithmic paradigm that follows the problem s ...

  5. 贪心算法(Greedy Algorithm)最小生成树 克鲁斯卡尔算法(Kruskal#39;s algorithm)

    克鲁斯卡尔算法(Kruskal's algorithm)它既是古典最低的一个简单的了解生成树算法. 这充分反映了这一点贪心算法的精髓.该方法可以通常的图被表示.图选择这里借用Wikipedia在.非常 ...

  6. 贪心算法(Greedy Algorithm)之霍夫曼编码

    文章目录 1. 贪心算法 2. 应用 2.1 找零钱 2.2 区间覆盖 2.3 霍夫曼编码 霍夫曼编码完整代码 1. 贪心算法 我们希望在一定的限制条件下,获得一个最优解 每次都在当前的标准下做出当下 ...

  7. 贪婪算法(greedy Algorithm)

    贪婪算法的应用: 相关算法练习题: LeetCode股票买卖的最佳时机 LeetCode判断子序列 LeetCode 分发饼干 LeetCode跳跃游戏 LeetCode加油站 一.简单调度问题: 给 ...

  8. 实验12 Greedy Algorithm练习题 答案与解析

    1-1 只有当局部最优跟全局最优解一致的时候,贪心法才能给出正确的解.(1分) T 1-2 Let S be the set of activities in Activity Selection P ...

  9. 【控制】贪心算法(GA,Greedy Algorithm)及 Matlab 实现

    文章目录 算法思路 应用实例 仿真 Ref. 算法思路 贪心算法一般按如下步骤进行: 建立数学模型来描述问题. 把求解的问题分成若干个子问题. 对每个子问题求解,得到子问题的局部最优解. 把子问题的解 ...

最新文章

  1. Core Animation1-简介
  2. Windows 10 周年更新后的 Edge 14 的 HierarchyRequestError 报错
  3. OpenCASCADE:使用 扩展数据交换XDE之入门
  4. LeetCode 1277. 统计全为 1 的正方形子矩阵(DP)
  5. ORB-SLAM2和ORB-SLAM的区别
  6. 我的Linux折腾史
  7. visual studio支持python吗_微软 Visual Studio Online 更新,更好地支持 Python 语言和 Docker...
  8. 各大科技公司都是如何使用CSS
  9. iOS 版本更新迭代
  10. clover config_【兵哥小课堂】不借助任何工具将CLOVER引导添加进UEFI的正确姿势
  11. WEP_密码破解教程_BT3_使用_(原创技术化)
  12. 计算机组成原理试题(三)(附参考答案)
  13. 三星手机性能测试软件,Exynos4210处理器性能测试_三星 I9100 GALAXY SII(16GB/黑色)_手机Android频道-中关村在线...
  14. python中callable什么意思_Python中的callable()
  15. GROMACS Tutorial 6-Free Energy Calculations
  16. 自动驾驶纯电动客车设计
  17. xctf攻防世界 MISC高手进阶区 2017_Dating_in_Singapore
  18. sublist3r报错ImportError: No module named dns.resolver
  19. H5项目2-3手机邮箱导航
  20. antd 表格树如何展开_antd design tree 怎样实现 :展开折叠全部树节点

热门文章

  1. IOS Masonry自动布局
  2. 安装Linux时,引导分区位于一个GPT分区方案的错误提示
  3. ORA-25153: Temporary Tablespace is Empty
  4. Kubernetes日志分析利器:Elassandra部署使用指南
  5. 第 3 章 镜像 - 010 - base 镜像
  6. Spring Cloud相关项目
  7. Module Zero之用户管理
  8. PHP文件上传,下载,Sql工具类!
  9. Spring的依赖注入和管理Bean
  10. quartz集群调度机制调研及源码分析---转载