1. 首页 / 百科

huffman编码 哈夫曼编码原理与Python实现代码 附手动推导过程原稿真迹

huffman编码 哈夫曼编码原理与Python实现代码 附手动推导过程原稿真迹

huffman编码

哈夫曼编码依据字符出现概率来构造异字头(任何一个字符的编码都不是其他字符的前缀)的平均长度最短的码字,通过构造二叉树来实现,出现频次越多的字符编码越短,出现频次越少的字符编码越长。为了演示哈夫曼编码原理,我在纸上简单推导了一下,见下图(字有点丑,请忽略这个小问题):

实现哈夫曼编码过程的Python代码如下:from heapq import heapify, heappush, heappopfrom itertools import countfrom collections import Counterfrom random import choicefrom string import ascii_letters, digits

def huffman(seq, frq):    #这里的count()依次生成0,1,2,3,4,…    #主要用来入堆时保持顺序    num = count()    #对原始列表进行堆化    trees = list(zip(frq, num, seq))    heapify(trees)    while len(trees)>1:        #弹出堆中频次最少的两个元素        #_表示不关心这个值        fa, _, a = heappop(trees)        fb, _, b = heappop(trees)        #合并后生成新节点,重新入堆        heappush(trees, (fa+fb, next(num), [a,b]))    #返回建好的二叉树        return trees[0][-1]

def codes(tree, prefix=”):    if len(tree) == 1:        #注意,这里不能合并成一个return (tree, prefix)语句        yield (tree, prefix)        return    #二叉树左边节点编码为0,右边节点编码为1    for bit, child in zip(’01’, tree):        #在父节点编码基础上,接上每个节点的编码        for pair in codes(child, prefix + bit):            yield pair

def main(seq):    #统计各字符频次    global temp    temp = Counter(seq)    #这里只是为了让输出结果更直观,但实际上会影响效率    for item in sorted(temp.items(), key=lambda x: x[1], reverse=True):        print(item)    print(‘=’*20)    #根据各字符出现频次,生成哈夫曼树    seq = list(temp.keys())    frq = [temp[t] for t in seq]    tree = huffman(seq, frq)    #根据哈夫曼树,返回各字符编码的生成器对象    return codes(tree)

letters = ascii_letters + digitsavgLength = 0#生成随机字符串,模拟信源信号seq = ”.join((choice(letters) for i in range(100)))print(seq+’n’+’=’*20)#按编码长度从小到大输出#这里只是为了让输出结果更直观,但实际上会影响效率for item in sorted(main(seq), key=lambda x: len(x[1])):    print(item)    avgLength += temp.get(item[0]) * len(item[1])    #计算并输出平均码长print(avgLength/len(seq))

huffman编码相关文章

相关推荐

  • 张家港市邮编是多少 苏州市张家港市的邮政编码

    张家港市邮编是多少 苏州市张家港市的邮政编码

    张家港市邮编是多少(苏州市张家港市的邮政编码),张家港市,社区,街道,张家港(Zhangjiagang) 邮编215600 区号0512每天一县:江苏省苏州市张家港市太史慈子义张家港市(320582),因张家港河而得名。1961年设立沙洲县,1986年改为县级张家港市。辖3个街道、7个镇:金港街道、后塍街道、德积街道、杨舍镇、塘桥镇、锦丰镇、乐余镇、凤凰镇、南丰镇、大新镇。另有现代农业示范园区(原...

  • word怎么每段开头空两格 首行缩进两个字符设置方法

    word怎么每段开头空两格 首行缩进两个字符设置方法

    word怎么每段开头空两格 首行缩进两个字符设置方法,方法,首行缩进,设置,字符,选择,功能,文档,鼠标单击,Word是常用的文字处理软件,其中很多功能都为文字编辑提供了很多方便,不仅让我们操作更灵活,更让我们的工作效率有所提高,今天就让我们一起来学习下Word中让每段开头空两格的方法。首先,我们打开一个需要进行编辑的文档,如下图所示:然后我们选择全部要设置空格的段落,并鼠标单击右键,选择“段落”功能,如下图所示:在段落对话框,鼠标单击“特殊格式”的下拉按钮,选择...

  • sub什么意思字母圈里(字符sub什么意思)

    sub什么意思字母圈里(字符sub什么意思)

    sub什么意思字母圈里(字符sub什么意思),字符,什么意思,字母,圈里,很多人对sub什么意思字母圈里(字符sub什么意思)这个问题比较感兴趣,这里,金色百科小编大浪就给大家详细解答一下。
    在字母圈中,sub也就是BratSub指的是m方,而这个m指特别喜欢违抗命令,爱撒娇的人,就像一个没长大的小孩子一样。字母圈指的是SM。sm就是虐待与受虐(英文sadomasochism)的简称,尤其在性方面。通常s是施虐方,m是受虐方,s也被叫做主人...

  • psk密码是什么意思(psk密码非法字符是什么意思)

    psk密码是什么意思(psk密码非法字符是什么意思)

    psk密码是什么意思(psk密码非法字符是什么意思),密码,非法字符,psk,很多人对psk密码是什么意思(psk密码非法字符是什么意思)这个问题比较感兴趣,这里,金色百科小编小安就给大家详细解答一下。
    PSK密码是预共享密钥,预共享密钥是用于验证L2TP/IPSec连接的Unicode字符串。可以配置“路由和远程访问”来验证支持预共享密钥的连接。许多操作系统都支持使用预共享密钥,包括WindowsServer2003家族和WindowsX...

  • 字符串是什么意思

    字符串是什么意思

    字符串是什么意思,字符串,字符串是什么意思很多人对这个问题比较感兴趣,这里,金色百科小编小张就给大家详细解答一下。
    (1)计算机编程中的字符串是什么意思?在c中,字符串是一串字符,以'\0'作为结束标志,它与整形不同,它相当于一个字符数组,比如:字符串"hello"就相当于下边的这个tmp的数组chartmp[6]={'h','e','l','l','o','\0'};(2)计算机编程中的字符串是什么意思?字符指类字形单位或符号,包括字母、...

  • 字符间距在哪里设置 Word文档调整字间距教程

    字符间距在哪里设置 Word文档调整字间距教程

    字符间距在哪里设置 Word文档调整字间距教程,调整,文档,方法,教程,字间距,步骤,单词,文本,文档文档如何调整间距?许多小合作伙伴经常需要调整Word文档中的一些类型,并且单词间距是其中之一。那么我们应该如何调整Word文档中字词中的单词间距?让我们在小编来看看你!操作方法:在Word 1中调整单词间距方法:第1步:打开Word,选择要调整单词间距的文本 - “选择”开始“选项卡 - ”中文版图标,如图所示。步骤2:单击它丢弃,选择调整宽度,如图所示。步骤3:...