赞
踩
贪心算法的核心思想可以总结为:贪心算法总是做出在当前看来最好的选择。
也就是说贪心算法并不从整体最优考虑,它所做出的选择只是在某种意义上的局部最优选择。当然,希望贪心算法得到的最终结果也是整体最优的。
虽然贪心算法不能对所有问题都得到整体最优解,但对许多问题它能产生整体最优解,如单源最短路经问题,最小生成树问题等。虽然在一些情况下,即使贪心算法不能得到整体最优解,但其最终结果却是最优解的很好近似。
假设你办了个广播节目,要让国内的 8 个重要城市的听众都收听得到。为此,你需要决定在哪些广播台播出。在每个广播台播出都需要支付费用,因此你力图在尽可能少的广播台播出。现有广播台名单如下。
广播台 | 覆盖地区 |
---|---|
K1 | 北京、上海、天津 |
K2 | 广州、北京、深圳 |
K3 | 成都、上海、杭州 |
K4 | 上海、天津 |
K5 | 杭州、大连 |
如何选择最少的广播台,让所有的城市都可以接收到信号?
每个广播台都覆盖特定的区域,不通过的广播覆盖的区域可能是重叠的。如何找出覆盖 8 个城市的最小广播台集合呢?
首先我们最容易想到的办法就是穷举法:
上面这个方法确实可以求得最终结果,但是问题在于 n 个广播台可能的集合有 2ⁿ 个,因此运行时间为 O(2ⁿ)。如果广播台不多,比如只有 5~10 个,这个方法倒还可行。但是一旦问题的规模变大,广播台的数量增多,需要的时间将激增。假设每秒可以计算出 10 个集合,那么所需的时间如下表所示:
广播台数量 | 需要的时间 |
---|---|
5 | 3.2 秒 |
10 | 102.4 秒 |
32 | 13.6 年 |
100 | 4 x 10²¹ 年 |
显然,使用穷举所有集合的方法不是一个明智的选择。
针对这类集合覆盖问题,贪心算法是一个比较合适的算法,虽然贪心算法不一定能够得到最优解,但是它可以得到非常接近的解。
对于本题,贪心算法的基本思想如下:
可以看到,使用贪心算法解决集合覆盖问题的思路贯彻着 “选择当下看来最好的选择” 这样的思想。简单来说就是走好每一步路,最终得到的结果必定不会太差。
贪心算法不仅简单,而且运行速度也很快。对于本题,贪心算法的运行时间为 O(n²),其中 n 为广播台的数量。
首先来说一下代码实现的思路:
cities
,存放所有的城市;broadcast
,广播站作为键,对应的城市作为值;selectedList
,用于存放已选择的广播站;selectedList
中;cities
中移除,同时将广播站从散列表中移除;完整的代码实现如下 :
public static void main(String[] args) {
HashMap<String, Set> broadcast = new HashMap<>(); // 用于存放广播和覆盖的城市
HashMap<String, Set> selectedList = new HashMap<>(<
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。