acdream 1220 哈夫曼树

来源:互联网 发布:ubuntu 硬盘大小 编辑:程序博客网 时间:2024/05/30 23:43

题意:求哈夫曼树的带权路径长度

解法:直接建树可解 然后其实不建树也可以做的 直接取得每个合并节点的权值就可以了

#include<queue>#include<stdio.h>#include<iostream>using namespace std;#define ll long long#define maxn 500010struct node{    int l,r,id;    ll w;    node(){l=0,r=0;}    bool operator<(node x)const{return w>x.w;}}e[maxn<<1];int top;ll ans;void dfs(int rt,int dep){    if(!e[rt].l&&!e[rt].r){ans+=dep*e[rt].w;return ;}    if(e[rt].l!=0)dfs(e[rt].l,dep+1);    if(e[rt].r!=0)dfs(e[rt].r,dep+1);}int main(){    ll x;int n;    top=0;    priority_queue<node>q;    scanf("%d",&n);        for(int i=1;i<=n;++i){        scanf("%lld",&x);e[i].w=x;e[i].id=i;        q.push(e[i]);    }//    printf("%lld\n",q.top().w);    top+=n;    ans=(ll)0;    node a,b;    while(q.size()>1){        a=q.top();q.pop();b=q.top();q.pop();//        printf("%lld %lld\n",a.w,b.w);        ++top;        e[top].w=a.w+b.w; e[top].id=top;        e[top].l=a.id,e[top].r=b.id;        q.push(e[top]);    }    int _id=q.top().id;    q.pop();//    for(int i=1;i<=5;++i)//        printf("l:%d r:%d id:%d w:%lld\n",e[i].l,e[i].r,e[i].id,e[i].w);    dfs(_id,0);    printf("%lld\n",ans);    return 0;}


0 0
原创粉丝点击