美文网首页
数据结构与算法基础-哈夫曼树

数据结构与算法基础-哈夫曼树

作者: SK_Wang | 来源:发表于2020-04-30 01:08 被阅读0次

假设有n个权值{w1, w2, ..., wn},试构造一颗有n个叶子结点的二叉树,每个叶子结点带权为wi,则其中带权路径长度WPL最小的二叉树称做最优二叉树赫夫曼树

构造赫夫曼树

赫夫曼算法:

  1. 根据给定的n个权值{w1, w2, ..., wn}构成N棵二叉树的集合F = {T1, T2,... , Tn},其中每棵而茶水Ti中只有一个带权为wi的跟结点,其左右子树均空。
  2. 在F中选取两颗跟结点的权值最小的树作为左右子树构造一棵新的二叉树,且置新的二叉树的跟结点的权值为其左、右树上跟结点的权值之和。
  3. 在F中删除这两棵树,同时将新得到的二叉树加入F中。
  4. 重复(2)(3),直到F只含一棵树为止。这棵树便是赫夫曼树。

代码实现

const int MaxValue = 10000;
const int MaxBit = 4;
const int MaxN = 10;

typedef struct HaffNode {
    int weight;
    int flag;
    int parent;
    int leftChild;
    int rightChild;
} HaffNode;

void Haffman(int weight[], int n, HaffNode *haffTree) {
    // 初始化
    for (int i = 0; i < 2 * n - 1; i++) {
        if (i < n) {
            haffTree[i].weight = weight[i];
        } else {
            haffTree[i].weight = 0;
        }
        
        haffTree[i].flag = 0;
        haffTree[i].parent = 0;
        haffTree[i].leftChild = -1;
        haffTree[i].rightChild = -1;
    }
    
    int j, m1, m2, x1, x2;
    for (int i = 0; i < n - 1; i++) {
        m2 = m1 = MaxValue;
        x2 = x1 = 0;
        for (j = 0; j < n + i; j++) {
            if (haffTree[j].weight < m1 && haffTree[j].flag == 0) {
                m2 = m1 = haffTree[j].weight;
                x2 = x1 = j;
            } else if (haffTree[j].weight < m2 && haffTree[j].flag == 0) {
                m2 = haffTree[j].weight;
                x2 = j;
            }
        }
        
        haffTree[x1].parent = n + i;
        haffTree[x1].flag = 1;
        
        haffTree[x2].parent = n + i;
        haffTree[x2].flag = 1;
        
        haffTree[n + i].weight = haffTree[x1].weight + haffTree[x2].weight;
        haffTree[n + i].leftChild = x1;
        haffTree[n + i].rightChild = x2;
    }
}

赫夫曼编码

哈夫曼编码是一种编码方式,该方法依据字符出现概率来构造异字头的平均长度最短的码字,一般就叫做Huffman编码。

哈夫曼思想就是依据使用的频率来最大化的节省字符存储空间。

代码实现

typedef struct Code {
    int bit[MaxBit];
    int start;
    int weight;
} Code;

void HaffmanCode(HaffNode haffTree[], int n, Code haffCode[]) {
    Code *cd = (Code *)malloc(sizeof(Code));
    int child, parent;
    for (int i = 0; i < n; i++) {
        cd->start = 0;
        cd->weight = haffTree[i].weight;
        child = i;
        parent = haffTree[child].parent;
        while (parent != 0) {
            if (haffTree[parent].leftChild == child) {
                cd->bit[cd->start] = 0;
            } else {
                cd->bit[cd->start] = 1;
            }
            
            cd->start++;
            child = parent;
            parent = haffTree[child].parent;
        }
        
        int temp;
        for (int j = cd->start - 1; j >= 0; j--) {
            temp = cd->start - 1 - j;
            haffCode[i].bit[temp] = cd->bit[j];
        }
        
        haffCode[i].start = cd->start;
        haffCode[i].weight = cd->weight;
    }
    free(cd);
}

相关文章

  • Huffman树及Huffman编码

    Huffman树及Huffman编码 一.实验目的 掌握哈夫曼树的构造算法、哈夫曼编码原理。 二.实验要求与内容 ...

  • 数据结构与算法基础-哈夫曼树

    假设有n个权值{w1, w2, ..., wn},试构造一颗有n个叶子结点的二叉树,每个叶子结点带权为wi,则其中...

  • 初识哈夫曼树

    何为哈夫曼树: 哈夫曼树是压缩算法中非常重要数据结构。百度百科解释:给定n个权值作为n个叶子节点,构造一棵二叉树,...

  • 构造哈夫曼树

    构造huffman树的算法: 算法思想:哈夫曼算法采用自底向上逐步合并的方法,构造哈夫曼树:步骤1)构造n颗单叶结...

  • 大师兄的数据结构学习笔记(九): 图

    大师兄的数据结构学习笔记(八): 哈夫曼树与哈夫曼编码[https://www.jianshu.com/p/7e4...

  • 哈夫曼编码

    实验目的: (1) 掌握二叉树的定义; (2) 掌握哈夫曼树和哈夫曼编码算法的实现。 实验内容: 实现一个哈夫曼编...

  • 最优树与哈夫曼编码

    大学的时候《离散数学》讲过哈夫曼算法,过了很多年后,只记得哈夫曼算法加压缩与解压上有很大优势,但不太记得哈夫曼算法...

  • 哈夫曼树

    数据结构——哈夫曼树 哈夫曼树又被称为最优二叉树,是指一类带权路径长度最小的二叉树,哈夫曼树的遍历不是唯一的,因为...

  • 【恋上数据结构与算法一】(十六)哈夫曼树

    哈夫曼编码(Huffman Coding) ◼ 哈夫曼编码,又称为霍夫曼编码,它是现代压缩算法的基础 ◼ 假设要把...

  • 数据结构与算法 - 哈夫曼树

    哈夫曼(David Huffman) 著名的 哈夫曼编码 发明人 戴维·霍夫曼于1999年10月17日因癌症去世,...

网友评论

      本文标题:数据结构与算法基础-哈夫曼树

      本文链接:https://www.haomeiwen.com/subject/bqmnwhtx.html