贪心算法-哈夫曼树-(树的建立,带权路径长度,哈夫曼编码)

本文介绍了哈夫曼树的基本概念,包括路径、路径长度和节点带权路径长度。详细阐述了如何通过贪心算法建立哈夫曼树,并提供了相应的代码实现。此外,还讲解了哈夫曼树的带权路径长度计算方法及哈夫曼编码的生成过程。
摘要由CSDN通过智能技术生成
哈夫曼树中的名词意思:(ps:本想画个图的不知这上面怎么弄,就没弄了)

树的权值:每个树节点所在的那个数字。

路径:两个节点之间所经过的分支。

路径长度: 某一路径上的分支条数。

节点带权路径长度: 节点的权值*该节点的路径长度。

树带权路径长度:所有叶子节点的带全路径长度之和。

树带权路径长度:所有叶子节点的带全路径长度之和。

建立哈夫曼树:单独将数组中的每个值作为一个节点,依次选出剩余节点的最小与次小,并将其合为树结构的一部分。代码为:

 
btreenode *CreateHuffman(int a[],int n)
{
    int i;
    btreenode *s[n+1], *ss;
    for(int i = 0;i<n;i++){
        s[i] = new btreenode;  //初始化s指针数组,使每个指针元素指向a数组中对应的元素结点
        s[i]->data = a[i];   //将树拆成森林,每棵树都只有一个根节点
        s[i]->left = s[i]->right = NULL;
    }
    for(int i  = 1;i<n;i++){        //进行 n-1次循环建立哈夫曼树
           int k = -1,t;           //k表示森林中具有最小权值的树根结点的下标,t为次最小的下标
        for(int j = 0;j<n;j++){   //k初始指向森林中第一棵树,t指向第二棵
                if(s[j]&&k==-1){
                   k = j;
                   continue;
                }
                if(s[j]){
                    t =  j;
                    break;
                }
        }
        for(int i = t;i<n;i++){   //从当前森林中求出最小权值树和次最小 ;
            if(s[i]){
                if(s[i]->data<s[k]->data){        //比最小树小
                    t = k;
                    k = i;
                }
                else if(s[i]->data<s[t]->data){  //比次小树小
                    
  • 12
    点赞
  • 43
    收藏
    觉得还不错? 一键收藏
  • 4
    评论
好的,我来回答你的问题。 求解Huffman编码问题的过程可以分为以下几步: 1. 统计每个字符出现的频率,将它们作为权值构建出一个森林。 2. 从森林中选择两棵权值最小的作为左右子构建一棵新的,其权值为左右子的权值之和。 3. 将新构建的加入到森林中,重复步骤2直到森林只剩下一棵为止。 4. 对于每个字符,从根节点开始遍历构建出它的哈夫曼编码,其中左子标记为0,右子标记为1。 5. 计算每个字符的带权路径值,即每个字符的权值与它的哈夫曼编码长度的乘积之和。 下面是使用贪心算法求解Huffman编码问题的示例: 假设有5个字符A、B、C、D、E,它们的权值分别为5、2、4、7、1。 1. 首先将每个字符的权值作为一个森林中的单独。 ``` A(5) B(2) C(4) D(7) E(1) ``` 2. 选择权值最小的两棵B和E作为左右子构建一棵新的,其权值为B和E的权值之和3,得到以下森林: ``` A(5) C(4) D(7) BE(3) / \ B(2) E(1) ``` 3. 选择权值最小的两棵A和C作为左右子构建一棵新的,其权值为A和C的权值之和9,得到以下森林: ``` D(7) BE(3) AC(9) / \ / \ B(2) E(1) A(5) C(4) ``` 4. 选择权值最小的两棵BE和C作为左右子构建一棵新的,其权值为BE和C的权值之和7,得到以下森林: ``` D(7) AC(9) BEC(7) / | \ A(5) B(2) C(4) E(1) ``` 5. 选择权值最小的两棵D和BEC作为左右子构建一棵新的,其权值为D和BEC的权值之和14,得到以下森林: ``` DBEC(14) AC(9) / \ D(7) BEC(7) / \ B(2) C(4) E(1) ``` 6. 选择权值最小的两棵AC和DBEC作为左右子构建一棵新的,其权值为AC和DBEC的权值之和23,得到以下森林: ``` Huffman Tree: H(23) / \ AC(9) DBEC(14) / / \ A(5) D(7) BEC(7) / \ / \ B(2) C(4) E(1) ``` 7. 对于每个字符,从根节点开始遍历构建出它的哈夫曼编码: ``` A: 0 B: 111 C: 10 D: 110 E: 1100 ``` 8. 计算每个字符的带权路径值: ``` A: 5*1 = 5 B: 2*3 = 6 C: 4*2 = 8 D: 7*2 = 14 E: 1*4 = 4 ``` 因此,构造的哈夫曼树为23,哈夫曼编码为A: 0, B: 111, C: 10, D: 110, E: 1100,带权路径值为A: 5, B: 6, C: 8, D: 14, E: 4。
评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值