哈夫曼编码(Huffman Coding)是一种编码方式,哈夫曼编码是可变字长编码(VLC)的一种。 Huffman于1952年提出一种编码方法,该方法完全依据字符出现概率来构造异字头的平均长 度最短的码字,有时称之为最佳编码,一般就叫作Huffman编码。 内容来自
www.stl.vc 哈夫曼编码是广泛地用于数据文件压缩的十分有效的编码方法。其压缩率通常在20%~90%之间。哈夫曼编码算法用字符在文件中出现的频率表来建立一个用0,1串表示各字符的最优表示方式。 给出现频率高的字符较短的编码,出现频率较低的字符以较长的编码,可以大大缩短总码长。 例如一个包含100,000个字符的文件,各字符出现频率不同,如下表所示。定长变码需要300,000位,而按表中变长编码方案,文件的总码长为: (45×1+13×3+12×3+16×3+9×4+5×4)×1000=224,000。 比用定长码方案总码长较少约45%。 内容来自
www.stl.vc 对每一个字符规定一个0,1串作为其代码,并要求任一字符的代码都不是其它字符代码的前缀。这种编码称为前缀码。 编码的前缀性质可以使译码方法非常简单。 表示最优前缀码的二叉树总是一棵完全二叉树,即树中任一结点都有2个儿子结点。 平均码长定义为: C++编程网 本文来自C++编程网 C++编程网 使平均码长达到最小的前缀码编码方案称为给定编码字符集C的最优前缀码。 哈夫曼提出构造最优前缀码的贪心算法,由此产生的编码方案称为哈夫曼编码。 哈夫曼算法以自底向上的方式构造表示最优前缀码的二叉树T。 算法以|C|个叶结点开始,执行|C|-1次的“合并”运算后产生最终所要求的树T。 在书上给出的算法huffmanTree中,编码字符集中每一字符c的频率是f(c)。以f为键值的优先队列Q用在贪心选择时有效地确定算法当前要合并的2棵具有最小频率的树。一旦2棵具有最小频率的树合并后,产生一棵新的树,其频率为合并的2棵树的频率之和,并将新树插入优先队列Q。经过n-1次的合并后,优先队列中只剩下一棵树,即所要求的树T。 算法huffmanTree用最小堆实现优先队列Q。初始化优先队列需要O(n)计算时间,由于最小堆的removeMin和put运算均需O(logn)时间,n-1次的合并总共需要O(nlogn)计算时间。因此,关于n个字符的哈夫曼算法的计算时间为O(nlogn) 。 C++编程网 以下是代码: C++编程网 package greedy;
www.stl.vc class HaffuManNode implements java.lang.Comparable{ public int compareTo(Object o) { if(f<((HaffuManNode)o).f) { return -1; } else if(f>((HaffuManNode)o).f) { return 1; } else { return 0; } } private double f; private HaffuManNode left; private HaffuManNode right; public HaffuManNode() { f=0; left=right=null; } public HaffuManNode(double f) { this.f=f; left=right=null; } 本文来自C++编程网 public double getF() { return f; } public void setF(double f) { this.f = f; } public HaffuManNode getLeft() { return left; } public void setLeft(HaffuManNode left) { this.left = left; } public HaffuManNode getRight() { return right; } public void setRight(HaffuManNode right) { this.right = right; }
www.stl.vc }
www.stl.vc