AcWing148 合并果子(哈夫曼贪心、优先队列)

题目:AcWing148 合并果子


前言

哈夫曼编码的结果是让各个使用频率不同的字符编码长度最小。合并果子这道题目可以合并非相邻的果子,自然是使用哈夫曼贪心。

一、题目陈述

假定每个果子重量都为1,并且已知果子的种类数和每种果子的数目,你的任务是设计出合并的次序方案,使达达耗费的体力最少,并输出这个最小的体力耗费值。
输入格式
输入包括两行,第一行是一个整数n,表示果子的种类数。
第二行包含n个整数,用空格分隔,第i个整数ai是第i种果子的数目。
输出格式
输出包括一行,这一行只包含一个整数,也就是最小的体力耗费值。
数据范围
1≤n≤10000,
1≤ai≤20000
输入样例
3
1 2 9
输出样例
15

二、解决思路

使用优先队列,每次都合并最小的两堆果子。因为合并果子不需要两堆果子必须相邻,所以是哈夫曼贪心。如果是要求必须相邻,就要考虑DP算法了。

三、代码实现

#include<iostream>
#include<queue>
#include<algorithm>
using namespace std;
int main() {
	int n;	cin>>n;
	priority_queue<int, vector<int>, greater<int>> heap;
	while(n --) {
		int x;	cin>>x;
		heap.push(x);
	}
	int res = 0;
	while(heap.size()>1) {
		int a=heap.top();	heap.pop();
		int b=heap.top();	heap.pop();
		res += a + b;
		heap.push(a+b);
	}
	cout<<res<<endl;
	return 0;
}

总结

使用了优先队列,每次合并最小的两堆果子。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

codertea

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值