贪心算法集锦

                                                                              1.普通贪心

2.进阶版贪心:(1)最小生成树

                           (2)HUMAN编码

                     (3)模拟退火


首先我们应该了解什么是贪心算法:贪心算法也就是得到在某种意义上的局部最优解,不是对所有问题都能得到整体最优解,关键是贪心策略的选择。

其次,对于一个具体问题,要确定它是否具有贪心选择性质,必须证明每一步所作的贪心选择最终导致问题的整体最优解。

贪心策略适用的前提是:局部最优策略能导致产生全局最优解。

废话少说,下面我们来看一个基础的贪心例题

1.普通贪心:

【硬币问题】

问题描述:
1元、5元、10元、50元、100元、500元的硬币各C1C5C10C50C100C500枚。现在要用这些硬币来支付A元,最少需要多少枚硬币?假设本题至少存在一种支付方案。
限制条件:
0<=C1C5C10C50C100C500<=109次方
0<= A <= 109次方

输入:
C1 = 3 C2 = 2 C10 = 1 C50 = 3 C100 = 0 C500 = 2 A = 620

输出:6500元硬币1枚,50元硬币2枚,10元硬币1枚,5元硬币2枚,合计6枚)

我们可以得到一个很简单的策略就是:优先使用面值大的硬币,所以贪心法就是每次选取最优策略。

#include<iostream> 
using namespace std;
//贪心算法
const int v[6] = {1,5,10,50,100,500};//硬币的面值
int c[6];//每种硬币的数量
int A;

void Solve() {
	int ans = 0;
	for(int i = 5; i >= 0; i--) {
		//先是大面值
		int t = min(A / v[i],c[i]);//不能超过硬币数量
		A -= t * v[i];
		ans += t;
	}
	cout<<ans;
}

int main(void) {
	for(int i = 0; i < 6; i++) {
		cin>>c[i];
	}
	cin>>A;
	Solve();
	return 0;
}

大家也可以看一下洛谷上边的P1208 [USACO1.3]混合牛奶 Mixing Milk, https://www.luogu.com.cn/problem/P1208,这也是一道基础的贪心题。这里我就不过多的讲解了,网站上面有题解非常详细。

下面到了我们今天的重点:进阶版贪心。


2.进阶版贪心:

                   (1)最小生成树:

                               也就是我在之前写过的无向图最小生成树那一题,https://blog.youkuaiyun.com/qq_57657120/article/details/118860597?spm=1001.2014.3001.5502,这是一道经典的最小生成树问题,具体方法在专栏里写的非常清楚。

                   (2)Human编码:

                          human编码一般来说用的方法是优先队列,关于此方法https://blog.youkuaiyun.com/HouszChina/article/details/72784261这个博主写的非常完整,在这里我就不过多的讲解了。下面我们来看一道例题:

【POJ1521 Entropy】输入一个字符串,分别用普通ASCII编码(每个字符8bit)和哈夫曼编码,输出编码后的长度,并输出压缩比。
【输入样例】AAAAABCD
【输出样例】64 13 4.9

 此题我在之前的专栏里也写过一道类似的,这个是翻译过来之后的简单一点的大致意思。

https://blog.youkuaiyun.com/qq_57657120/article/details/119034792?spm=1001.2014.3001.5502大家可以研究一下。

                    (3)模拟退火:

                              个人认为此处是整个贪心算法中最不好懂的一种类型。那么,什么是模拟退火呢?

                             模拟退火算法来源于固体退火原理,是一种基于概率的算法,将固体加温至充分高,再让其徐徐冷却,加温时,固体内部粒子温升变为无序状,内能增大,而徐徐冷却时粒子渐趋有序,在每个温度都达到平衡态,最后在常温时达到基态,内能减为最小。

                             看了上述解释之后是不是觉得头大,其实我开始在网上搜索的时候也是这个一脸懵,个人认为官方解释虽然准确,但是很难让人快速了解。在网上搜索之后,我觉得c.biancheng.net/view/507.html这个博主写的是非常详细的,大家可以参考一下。了解之后,我们来看一个例题。

由于题目过长,我就直接放链接了:http://poj.org/problem?id=2069

本题又名最小球覆盖,

1.对于一个点,球心就是这个点且半径无穷小。

2.对于两个点,球心是两个点线段的中点,半径就是线段长度的一半。

3.对于三个点,三个点构成的平面必为球的大圆,所以球心是三角形的外心,半径就是球心到某个点的距离。

4.对于四个点,若四个点共面则转化到3,只需考虑某三个点的情况,若四点不共面,四面体可以唯一确定一个外接球。

5.对于五个及以上点,其最小球必为其中某4个点的外接球(假设不全共面)。

我们从第五点可以知道,对于球心距离最远最多4个等距离的其他点。

所以我们随机选取一个点之后,逐渐靠近球心,让球心达道稳定态即可。

            

            

      

      

    

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值