算法其实很简单—贪心算法

目录

1. 贪心算法介绍

2. 应用场景—集合覆盖问题

2.1 思路分析

3. 代码


1. 贪心算法介绍

算法可以贪心,人不能贪心哦~

  1. 贪婪算法(贪心算法)是指在对问题进行求解时,在每一步选择中都采取最好或者最优(即最有利)的选择,从而希望能够导致结果是最好或者最优的算法
  2. 贪婪算法所得到的结果不一定 是最优的结果(有时候会是最优解),但是都是相对近似(接近)最优解的结果

 

2. 应用场景—集合覆盖问题

 

2.1 思路分析

➢ 如何找出覆盖所有地区的广播台的集合呢,使用穷举法实现,列出每个可能的广播台的集合,这被称为幂集。假设总的有n个广播台,则广播台的组合总共有2n -1个,假设每秒可以计算10个子集,如图:

➢ 使用贪婪算法,效率高:目前并没有算法可以快速计算得到准备的值,使用贪婪算法,则可以得到非常接近的解,并且效率高。选择策略上,因为需要覆盖全部地区的最小集合:

  1. 遍历所有的广播电台,找到一个覆盖了最多未覆盖的地区的电台(此电台可能包含一些己覆盖的地区,但没有关系)
  2. 将这个电台加入到一个集合中(比如ArrayList),想办法把该电台覆盖的地区在下次比较时去掉。
  3. 重复第1步直到覆盖了全部的地区

3. 代码

package com.example.datastructureandalgorithm.greedy;

import java.util.*;

/**
 * @author 浪子傑
 * @version 1.0
 * @date 2020/6/15
 */
public class GreedyDemo {
    public static void main(String[] args) {
        // 创建电台,放入map
        Map<String, Set<String>> broadcasts = new HashMap<String, Set<String>>();
        Set set1 = new HashSet<String>();
        set1.add("北京");
        set1.add("上海");
        set1.add("天津");

        Set set2 = new HashSet<String>();
        set2.add("广州");
        set2.add("北京");
        set2.add("深圳");

        Set set3 = new HashSet<String>();
        set3.add("成都");
        set3.add("上海");
        set3.add("杭州");

        Set set4 = new HashSet<String>();
        set4.add("上海");
        set4.add("天津");

        Set set5 = new HashSet<String>();
        set5.add("杭州");
        set5.add("大连");

        broadcasts.put("K1", set1);
        broadcasts.put("K2", set2);
        broadcasts.put("K3", set3);
        broadcasts.put("K4", set4);
        broadcasts.put("K5", set5);

        // 存放所有的地区
        Set allAreas = new HashSet<String>();
        allAreas.add("北京");
        allAreas.add("上海");
        allAreas.add("杭州");
        allAreas.add("天津");
        allAreas.add("成都");
        allAreas.add("大连");
        allAreas.add("广州");
        allAreas.add("深圳");

        // 存放选择的电台
        List selects = new ArrayList<String>();

        // 循环,直到allAreas大小为0
        while (allAreas.size() != 0) {
            // 中间变量,存放选择的最大的电台key
            String maxKey = null;
            // 循环所有的电台
            for (String key : broadcasts.keySet()) {
                // 中间变量,用来存放当前key和allAreas的交集
                Set<String> tempSet = new HashSet<>();
                // 获取key对应的所有地区
                Set<String> areas = broadcasts.get(key);
                // 将当前key的地区放入中间变量
                tempSet.addAll(areas);
                // 求出当前key和allAreas的交集
                tempSet.retainAll(allAreas);
                // 如果交集不为空,并且
                // 最大电台的maxKey为空或者交集大于maxKey对应的地区的时候
                // 需要重置maxKey
                if (tempSet.size() > 0 &&
                        (maxKey == null || tempSet.size() > broadcasts.get(maxKey).size())) {
                    maxKey = key;
                }
            }
            if (maxKey != null) {
                selects.add(maxKey);
                allAreas.removeAll(broadcasts.get(maxKey));
            }
        }

        System.out.println(selects);
    }
}

猜你喜欢

转载自blog.csdn.net/guozhangjie1992/article/details/106772696