python实现--哈夫曼编码

哈夫曼树(Huffman Tree)和哈夫曼编码(Huffman Coding)是一种用于数据压缩的技术,由David A. Huffman于1952年提出。哈夫曼树是一种特殊的二叉树,用于构建哈夫曼编码。哈夫曼编码是一种变长编码,用于将字符映射到不同长度的比特串,以实现数据的高效压缩。

哈夫曼树

构建哈夫曼树

哈夫曼树是一种带权路径长度最短的树,即权值越大的节点离根节点越近。
构建哈夫曼树的基本思想是:从所有权值为正整数的叶子节点开始,每次选取两个权值最小的节点合并成一个新的节点,直到最后只剩下一个根节点为止。

哈夫曼树的性质

哈夫曼树是一棵满二叉树(所有非叶子节点的度都是2)。
树中的每个叶子节点代表一个字符,其权值即为字符出现的频率。
哈夫曼树的带权路径长度(WPL)最小,即每个字符的编码长度最短。

哈夫曼编码

构建哈夫曼编码
哈夫曼编码是一种前缀编码,即没有任何一个字符的编码是另一个字符编码的前缀。
从哈夫曼树的根节点开始,沿着左子树路径走一步,编码为0;沿着右子树路径走一步,编码为1。
将所有字符根据哈夫曼树的路径映射到对应的编码。

构建哈夫曼树的基本思想和步骤:
步骤一:统计字符频率:
遍历待编码的字符串或者字符流,统计每个字符出现的频率。
步骤二:构建哈夫曼树:
将每个字符和其对应的频率作为叶子节点,构建一个包含所有叶子节点的森林。
每次从森林中选择两个权值最小的树(即叶子节点),合并成一个新的树,新树的权值为两个子树的权值之和。
不断重复上述合并步骤,直到森林中只剩下一棵树为止,这棵树即为哈夫曼树。
步骤三:生成哈夫曼编码:
根据构建好的哈夫曼树,从根节点开始,沿着左子树路径走一步编码为0,沿着右子树路径走一步编码为1,直到到达叶子节点。
将每个字符根据路径映射到对应的编码。

import heapq
from collections import defaultdict

class TreeNode:
    def __init__(self, char, freq):
        self.char = char
        self.freq = freq
        self.left = None
        self.right = None

    def __lt__(self, other):
        return self.freq < other.freq

def build_huffman_tree(text):
    # 统计字符频率
    freq_map = defaultdict(int)
    for char in text:
        freq_map[char] += 1
    
    # 创建优先队列(最小堆)用于构建哈夫曼树
    priority_queue = [TreeNode(char, freq) for char, freq in freq_map.items()]
    heapq.heapify(priority_queue)
    
    # 构建哈夫曼树
    while len(priority_queue) > 1:
        left = heapq.heappop(priority_queue)
        right = heapq.heappop(priority_queue)
        merged_node = TreeNode(None, left.freq + right.freq)
        merged_node.left = left
        merged_node.right = right
        heapq.heappush(priority_queue, merged_node)
    
    # 返回哈夫曼树的根节点
    return priority_queue[0]

def generate_huffman_codes(root):
    def dfs(node, code, result):
        if node:
            if node.char:
                result[node.char] = code
            dfs(node.left, code + '0', result)
            dfs(node.right, code + '1', result)
    
    huffman_codes = {}
    dfs(root, '', huffman_codes)
    return huffman_codes

# 测试
text = "ABRACADABRA"
huffman_tree = build_huffman_tree(text)
huffman_codes = generate_huffman_codes(huffman_tree)

print("Huffman Codes:")
for char, code in huffman_codes.items():
    print(f"{char}: {code}")

以上代码首先定义了TreeNode类来表示哈夫曼树的节点,然后实现了build_huffman_tree函数来构建哈夫曼树,generate_huffman_codes函数来生成哈夫曼编码。在build_huffman_tree函数中,我们使用了优先队列(最小堆)来构建哈夫曼树,通过不断合并权值最小的节点来构建整棵树。在generate_huffman_codes函数中,我们使用深度优先搜索(DFS)来遍历哈夫曼树,生成每个字符的哈夫曼编码。最后,打印出生成的哈夫曼编码。

哈夫曼编码的优势

哈夫曼编码根据字符出现的频率,将出现频率高的字符编码成短比特串,出现频率低的字符编码成长比特串,从而实现数据的高效压缩。
由于哈夫曼编码是前缀编码,所以在解码时不会出现歧义,可以根据编码直接还原出原始数据。

  • 6
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值