题目1172:哈夫曼树(最短路径的和)

题目1172:哈夫曼树

时间限制:1 秒

内存限制:32 兆

特殊判题:

题目描述:

哈夫曼树,第一行输入一个数n,表示叶结点的个数。需要用这些叶结点生成哈夫曼树,根据哈夫曼树的概念,这些结点有权值,即weight,题目需要输出所有结点的值与权值的乘积之和。

输入:

输入有多组数据。
每组第一行输入一个数n,接着输入n个叶节点(叶节点权值不超过100,2<=n<=1000)。

输出:

输出权值。

样例输入:
5
1 2 2 5 9
样例输出:
37
#include <iostream>
#include<stdio.h>
#include<queue>
using namespace std;
priority_queue<int,vector<int>, greater<int> > Q;//建立一个小顶堆,注意最后的> >要分开写
int main()
{
    int n;
    while(scanf("%d",&n)!=EOF)
    {
        while(Q.empty()==false) Q.pop();//清空堆中元素
        for(int i=0; i<n; i++)
        {
            int x;
            scanf("%d",&x);
            Q.push(x);//权值放入堆中
        }
        int ans=0;
        while(Q.size()>1)
        {
            int a=Q.top();
            Q.pop();
            int b=Q.top();
            Q.pop();
            ans+=a+b;//父亲节点必为非叶子节点,故累加其权值
            Q.push(a+b);//将双亲节点的权值放回堆中
        }
        printf("%d\n",ans);
    }
    return 0;
}
#include <iostream>
#include<stdio.h>
#include<queue>
#include<algorithm>
using namespace std;
int a[102];
bool  cmp(int a,int b)
{
    return a<b;
}

int main()
{
    int n;
    while(scanf("%d",&n)!=EOF)
    {
        for(int i=0;i<n;i++)
        {
            scanf("%d",&a[i]);
        }

        int sum=0;
        for(int i=0;i<n-1;i++)
        {
            sort(a,a+n,cmp);//每一次都要重新排序
            a[i+1]+=a[i];
            sum+=a[i+1];
        }
        printf("%d\n",sum);
    }
    return 0;
}

/**************************************************************
    Problem: 1172
    User: zhuoyuezai
    Language: C++
    Result: Accepted
    Time:30 ms
    Memory:1520 kb
****************************************************************/

时间: 2024-10-09 10:00:49

题目1172:哈夫曼树(最短路径的和)的相关文章

POJ 3253 Fence Repair(优先队列,哈夫曼树)

题目 //做哈夫曼树时,可以用优先队列(误?) //这道题教我们优先队列的一个用法:取前n个数(最大的或者最小的) //哈夫曼树 //64位 //超时->优先队列,,,, //这道题的优先队列用于取前2个小的元素 #include <iostream> #include<stdio.h> #include<string.h> #include<algorithm> #include<queue> using namespace std; _

BUPT复试专题—哈夫曼树

题目描述 哈夫曼树,第一行输入一个数n,表示叶结点的个数.需要用这些叶结点生成哈夫曼树,根据哈夫曼树的概念,这些结点有权值,即weight,题目需要输出所有结点的值与权值的乘积之和. 输入描述: 输入有多组数据.每组第一行输入一个数n,接着输入n个叶节点(叶节点权值不超过100,2<=n<=1000). 输出描述: 输出权值. 示例1 输入 5 1 2 2 5 9 #include<iostream> #include<cstdio> #include<cmath

九度oj 题目1172:哈夫曼树

题目描述: 哈夫曼树,第一行输入一个数n,表示叶结点的个数.需要用这些叶结点生成哈夫曼树,根据哈夫曼树的概念,这些结点有权值,即weight,题目需要输出所有结点的值与权值的乘积之和. 输入: 输入有多组数据. 每组第一行输入一个数n,接着输入n个叶节点(叶节点权值不超过100,2<=n<=1000). 输出: 输出权值. 样例输入: 5 1 2 2 5 9 样例输出: 37 一开始本来想用数组来构造哈夫曼树,代码如下: 1 #include <cstdio> 2 #include

关于【哈夫曼树】

为了方便快捷高效率的求得集合中权值最小的2个元素,我采用堆数据结构,它可以以O(logn)的复杂度取得n个元素中的最小值.为了绕过对堆的实现,我采用标准模板库中的相应标准模板——优先队列. 利用语句: priority_queue<int> Q; 建立一个保存元素为int的堆Q,但是此时建立的堆默认是大顶堆,即每次取到的元素是整个堆中的最大元素,于是采用如下语句定义一个小顶堆: priority_queue<int,vector<int>,greater<int>

数据结构_哈夫曼树

基本概念 路径:在一棵树中,从任意一个结点到达另一个结点的通路 路径长度:该路径所需经过的边的个数 带权路径长度:从根结点到达该节点的路径长度再乘以该结点权值的结果 带权路径长度和:树所有的叶子结点的带权路径长度和 哈夫曼树:给定n个带权值结点,以它们为叶子结点构造的一棵带权路径和最小的二叉树 哈夫曼树的求法 将所有结点放入集合 K. 若集合 K 中剩余结点大于 2 个,则取出其中权值最小的两个结点,构造他们同时为某个新节点的左右儿子,该新节点是他们共同的双亲结点,设定它的权值为其两个儿子结点的

哈夫曼树与哈夫曼编码

哈夫曼树与哈夫曼编码 术语: i)路径和路径长度 在一棵树中,从一个结点往下可以达到的孩子或孙子结点之间的通路,称为路径. 路径中分支的数目称为路径长度.若规定根结点的层数为1,则从根结点到第L层结点的路径长度为L-1. ii)结点的权及带权路径长度 若对树中的每个结点赋给一个有着某种含义的数值,则这个数值称为该结点的权. 结点的带权路径长度为:从根结点到该结点之间的路径长度与该结点的权的乘积. iii)树的带权路径长度 树的带权路径长度:所有叶子结点的带权路径长度之和,记为WPL. 先了解一下

hdu5884 Sort(二分+k叉哈夫曼树)

题目链接:hdu5884 Sort 题意:n个有序序列的归并排序.每次可以选择不超过k个序列进行合并,合并代价为这些序列的长度和.总的合并代价不能超过T, 问k最小是多少. 题解:先二分k,然后在k给定的情况下,构造k叉哈夫曼树.O(nlogn)的做法:先对所有数排序,另外一个队列维护合并后的值,取值时从两个序列前端取小的即可. 注:如果(n-1)%(k-1)!=0,那么就要增加(k-1-(n-1)%(k-1))个权值为0的叶子节点作虚拟点. 1 #include<cstdio> 2 #inc

哈夫曼树以及哈夫曼编码的问题

今天看到一个哈夫曼编码的题目,给定一个字符串abcdabaa,问哈夫曼编码后的二进制串的总长度是多少,答案是14 对于哈夫曼树我是一点都不了解啊,所以一顿查找,总结出以下知识点,与大家分享:当然部分内容参考了下百度 哈夫曼树又称为最优二叉树,是一种带权路径最短的二叉树.哈夫曼树是二叉树的一种应用,在信息检索中很常用. 一些相关的概念: 1.节点之间的路径长度:从一个节点到另一个节点之间的分支数量称为两个节点之间的路径长度. 2.树的路径长度:从根节点到树中每一个节点的路径长度之和. 3.节点的带

贪心(哈夫曼树):HDU 5884 sort

这道题目,我做的时候不会哈夫曼树,自己贪心是错的都不知晓.还可以发现这里不必用优先队列,可以用两个队列,毕竟插入的数是有单调性的. 1 #include <algorithm> 2 #include <iostream> 3 #include <cstring> 4 #include <cstdio> 5 using namespace std; 6 const int N=300010; 7 int a[N],n,S,f1,f2,b1,b2; 8 int