首页 > 其他 > 详细

哈夫曼树

时间:2019-06-23 10:00:52      阅读:81      评论:0      收藏:0      [点我收藏+]

题目描述

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

输入

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

输出

输出权值。

样例输入

2
2 8
3
5 11 30

样例输出

10
62

#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<map>
#include<stack>
#include<queue>
#define ll long long
using namespace std;
ll n,ans,h[5020];
struct E{
    ll k,l,r,t;
    friend bool operator < (E x,E y){return x.k>y.k;}
}e[5020];
priority_queue<E>q;
void dfs(ll root){
    if(root==0) return;
    ll ls=e[root].l,rs=e[root].r;
    h[ls]=h[rs]=h[root]+1;
    if(ls==0&&rs==0){
        ans+=e[root].k*h[root];
    }
    dfs(ls);
    dfs(rs);
}
int main(){
    while(cin>>n){
        ll cur=n;ans=0;
        memset(h,0,sizeof(h));
        for(ll i=1;i<=n;i++){
            ll x;
            cin>>x;
            e[i].k=x;
            e[i].l=0;
            e[i].r=0;
            e[i].t=i;
            q.push(e[i]);
        }
        while(q.size()>1){
            E xx=q.top();q.pop();
            E yy=q.top();q.pop();
            //cout<<xx.k<<' '<<yy.k<<endl;
            E neww=(E){xx.k+yy.k,xx.t,yy.t,++cur};
            e[cur]=neww;
            q.push(neww);
        }
        E root=q.top();q.pop();
        h[root.t]=0;
        dfs(root.t);
        /*for(int i=1;i<=cur;i++){
            cout<<e[i].k<<' '<<e[i].l<<' '<<e[i].r<<' '<<e[i].t<<endl;
        }*/
        cout<<ans<<endl;
    }
    return 0;
}

哈夫曼树

原文:https://www.cnblogs.com/sz-wcc/p/11071867.html

(0)
(0)
   
举报
评论 一句话评论(0
关于我们 - 联系我们 - 留言反馈 - 联系我们:wmxa8@hotmail.com
© 2014 bubuko.com 版权所有
打开技术之扣,分享程序人生!