一、霍夫曼编码的原理:
在数据通信时,可以用0,1码的不同排列来表示字符。例如给定一段报文CAST CAST SAT AT A TASA
,在报文中出现的字符集合是{C,A,S,T},各个字符出现的频度是{2,7,4,5}。若给每个字符一个等
长的二进制表示,例如 C:00 A:01 S:10 T:11,则所发的报文将是00011011 00011011 100111 0111 01 11011001,
共计(2+7+5+4)*2=36个码。若按字符出现的频度不同给予不同长度的编码,出现频度较大的字符采用
为数较少的编码,出现频度较小的字符采用位书较多的编码,可以是报文的码数降到最小,这就是所谓的最小
冗余编码问题。霍夫曼编码就能实现这种最小冗余编码。上例中按字符出现的频度进行编码,A:0 T:10 S:110
C:111,则最终的报文只有35个码,节省了传输中使用的单元。
二、核心算法:
一般情况下,霍夫曼编码的工作主要分为两步。第一步是准备工作,对于需要编码的字符(一般存在于文件里)
进行扫描,统计每个字符出现的频次,得到一个整数数组。第二步根据这个频次数组构造一棵霍夫曼树,这一步
是霍夫曼编码的核心内容。第三步,再次扫描一遍待编码的字符,对每个字符,在霍夫曼树里搜索该字符,得到它的编码。
用到的主要数据结构包括:最小堆、二叉树和栈。
算法1:构造霍夫曼树 //////////////////////
输入:频次数组weights[]
输出:频次的霍夫曼树(是一种二叉树)
过程:
1 扫描频次数组weights
针对每个weights[i],构造一个单节点二叉树,插入最小堆中;
2 设weights长度为n,循环n-1次
每次循环都选择二叉树里根的值较小的两棵进行合并,新生成的树
的根的值=旧的两棵树根的值的和,旧的被合并的两棵二叉树被从
最小堆里删除,新合并生成的二叉树插入到最小堆里;
3 最后最小堆里只剩下一棵二叉树,它就是要求的霍夫曼树
算法2:编码算法 //////////////////////////
//从树根开始在HFTree里查找w,向左走记为0
//向右走记为0,最终的01串就是w的编码。
//算法思想类似于二叉树的非递归遍历算法,
//利用栈来存放上一个树节点的信息,
输入:霍夫曼树HFTree,待编码的权值w
输出:编码字符串 str
过程:
1 声明遍历树节点的变量currno

本文介绍了霍夫曼编码的原理,通过最小冗余编码减少传输中的码数。核心算法包括构造霍夫曼树和编码算法,使用了最小堆、二叉树和栈的数据结构。文章详细阐述了两个关键步骤的实现:一是根据字符频度构建霍夫曼树,二是遍历霍夫曼树获取字符编码。并提供了C++实现霍夫曼编码的代码示例。

4007

被折叠的 条评论
为什么被折叠?



