字符拥有权重后的哈夫曼编码

来源:互联网 发布:品质365 知乎 编辑:程序博客网 时间:2024/06/02 03:37

哈夫曼编码 

/*Name: 哈夫曼编码 Copyright: Author: cc Date: 02/05/17 18:33Description: 自己的笔记,希望以后用到的时候能用到 */#include<iostream> #include<iomanip>using namespace std;typedef struct{char data;double weight;int parent;int lchild;int rchild;}HTNode;//哈夫曼树中每个元素的结构 typedef struct{char cd[12];int start;}HCode;//设置哈夫曼编码所需结构 void CreateHT(HTNode ht[],int n)//构造哈夫曼树 {int i,j,k,lnode,rnode;double min1,min2;for(i=0;i<2*n-1;i++)ht[i].parent=ht[i].lchild=ht[i].rchild=-1;//设置标志位-1,表示未进行华夫曼树构造 for(i=n;i<2*n-1;i++){min1=min2=32767;lnode=rnode=-1;for(k=0;k<=i-1;k++)if(ht[k].parent==-1){if(ht[k].weight<min1){min2=min1;rnode=lnode;//每次从未进行构造的数中找出 最小的两个数 min1=ht[k].weight;lnode=k;}else if(ht[k].weight<min2)  {min2=ht[k].weight;rnode=k;  }}ht[i].weight=ht[lnode].weight+ht[rnode].weight;//将所得两个数进行组合,构造哈夫曼树 ht[i].lchild=lnode;ht[i].rchild=rnode;ht[lnode].parent=i;ht[rnode].parent=i;}}char CreateHCode(HTNode ht[],HCode hcd[],int n)//将哈夫曼树进行哈夫曼编码 {int i,f,c;HCode hc;for(i=0;i<n;i++){hc.start=n;c=i;f=ht[i].parent;cout<<ht[i].data;//依次输出字符 while(f!=-1)//若不是根节点则进行循环 {if(ht[f].lchild==c)hc.cd[hc.start--]='0';//当前节点是双亲节点的左孩子节点 elsehc.cd[hc.start--]='1';//当前节点是双亲节点的右孩子节点c=f;f=ht[f].parent;//对双亲节点做上述相同操作 }hc.start++;  //start指向哈夫曼编码的开始字符 hcd[i]=hc;for(int j=hc.start;j<=n;j++)//输出字符对应最后构造的编码结果 cout<<hc.cd[j];cout<<endl; }}int main(){HTNode htn[15];HCode hcd[8];  //初始值与权重设置 htn[0].data='a';htn[0].weight=0.07;htn[1].data='b';htn[1].weight=0.19;htn[2].data='c';htn[2].weight=0.02;htn[3].data='d';htn[3].weight=0.06;htn[4].data='e';htn[4].weight=0.32;htn[5].data='f';htn[5].weight=0.03;htn[6].data='g';htn[6].weight=0.21;htn[7].data='h';htn[7].weight=0.1;CreateHT(htn,8);    CreateHCode(htn,hcd,8);     cout<<"999算法666";return 0;}