ESC
输入关键词搜索文章
目录

数据压缩

信息论 · 第5-6章
熵给出极限,编码把极限逼近成可执行算法
2核心定理
4典型编码法
1Kraft 不等式
3完整例题
第5-6章
为什么压缩有极限

数据压缩看起来像一个工程问题:给文本、图像、语音找一种更短的表示方式,节省存储和传输成本。但信息论把它变成了一个更尖锐的问题:

给定信源分布 $p(x)$,在完全无损恢复的前提下,平均至少要用多少个符号来表示一个信源符号?

这个问题分两层回答:

  1. 理论层:熵 $H(X)$ 决定了任何无损压缩都绕不过去的下界。
  2. 构造层:Shannon 码、Huffman 码、Shannon-Fano-Elias 编码、算术编码分别提供了不同程度逼近这个下界的办法。

第5章解决"极限在哪里",第6章解决"怎么逼近这个极限"。读这两章时,最重要的主线不是背算法,而是始终围绕下面这条链条:

信源分布 $\to$ 可译码约束 $\to$ 码长分配 $\to$ 平均码长 $\to$ 熵下界 $\to$ 具体构造

PDF数据压缩章节导入p.1
正在渲染 PDF 第 1 页…
数据压缩章节导入(PDF 第 1 页) · 打开原文
5.1
信源编码问题:我们到底在优化什么

设离散信源随机变量为 $X$,取值集合为 $\mathcal{X}=\{x_1,\dots,x_m\}$,概率分布为 $p(x)$。一个 $D$ 元信源编码 $C$ 把每个符号映射成一个由 $D$ 个码元组成的有限长字符串:

$$C: \mathcal{X} \to \mathcal{D}^*$$

其中:

  • $\mathcal{D}$ 是大小为 $D$ 的码字字母表,例如二进制时 $\mathcal{D}=\{0,1\}$
  • $\mathcal{D}^*$ 表示所有有限长字符串的集合
  • $l(x)$ 表示符号 $x$ 的码字长度

若按概率 $p(x)$ 发送符号,则编码的期望长度定义为:

$$L(C)=\sum_{x\in\mathcal{X}} p(x)l(x)$$

这就是压缩问题的目标函数。我们希望 $L(C)$ 越小越好。

但并不是随便给高概率符号分短码、低概率符号分长码就行。编码还必须满足可译码性,否则接收端无法唯一恢复原消息。

几种重要的编码类型

  • 非奇异码:不同源符号对应不同码字。
  • 唯一可译码:任意有限长源符号序列的编码结果都能唯一反解。
  • 前缀码 / 即时码:没有任何一个码字是另一个码字的前缀,从左到右读码时不必等后续符号即可立刻判定边界。

信源编码系统框图

graph LR
    A["信源符号
X ~ p(x)"] --> B["编码器
C(x)"] B --> C["码字序列
011001..."] C --> D["译码器
C⁻¹"] D --> E["恢复符号
X̂"] style A fill:#dbeafe,stroke:#2563eb style E fill:#dcfce7,stroke:#16a34a style B fill:#fef3c7,stroke:#d97706 style D fill:#fef3c7,stroke:#d97706

编码器将每个信源符号映射为码字,译码器将码字序列唯一恢复为信源符号序列。设计目标:在保证唯一可译的前提下,最小化平均码长。

前缀码最容易实现,也最重要。很多定理先对前缀码证明,再推广到唯一可译码。

为什么前缀码这么关键? 因为压缩的本质是"把常见符号缩短",这会让码字长度不等。长度一旦不等,就必须解决边界识别问题。前缀码用一个非常强的结构条件,直接保证边界瞬时可判。
PDF信源编码定义与目标p.2
正在渲染 PDF 第 2 页…
信源编码定义与目标(PDF 第 2 页) · 打开原文
5.2
Kraft 不等式:可行码长必须占得下码树

一旦进入可变长编码,最核心的问题就变成:哪些码长分配是可实现的? Kraft 不等式给出精确答案。

Kraft 不等式

$l_1,l_2,\dots,l_m$ 是某个 $D$ 元前缀码的码长,则必有

$$\sum_{i=1}^{m} D^{-l_i} \le 1$$

反过来,若一组正整数码长满足该不等式,则一定存在一个对应的 $D$ 元前缀码。

码树几何直观:为什么是 $D^{-l_i}$

把所有可能码字想成一棵 $D$ 叉树:

  • 树根是空串,第 1 层有 $D$ 个长度为 1 的串,第 $l$ 层一共有 $D^l$ 个长度为 $l$ 的字符串。
  • 一个长度为 $l_i$ 的码字,相当于在第 $l_i$ 层占据了一个叶子节点。
  • 由于前缀码要求码字之间不能互为前缀,一个叶子一旦被占,它下面整棵子树都不能再放别的码字。

如果把第 $l_i$ 层的一个叶子折算成"整棵树容量"的比例:

$$\frac{\text{该叶子占用的节点数}}{\text{第 }l_i\text{ 层总节点数}}=\frac{D^{l_i-1}}{D^{l_i}}=\frac{1}{D^{l_i}}=D^{-l_i}$$

所有码字占用总量不能超过整棵树容量 1,于是得到 $\sum D^{-l_i} \le 1$

充分性证明思路(构造性)

给定一组满足 $\sum D^{-l_i}\le 1$ 的正整数 $l_i$,如何构造前缀码?

  1. 把所有符号按码长从小到大排序:$l_{(1)}\le l_{(2)}\le\cdots\le l_{(m)}$
  2. 按顺序逐一分配码字:维护当前可用节点集合(初始为根)
  3. 每次取当前队列中第一个可用节点,从它往下走 $l_i$ 步得到的叶子即作为码字
  4. 该叶子被占后,其所有祖先保持可用(以支持同层其他码字),但该叶子以下子树标记为不可用

不等式保证整个过程中队列永远不会为空——容量始终够用。

一个直观例子

设二进制码长为 $(1,2,3,3)$,则

$$2^{-1}+2^{-2}+2^{-3}+2^{-3}=\frac12+\frac14+\frac18+\frac18=1$$

这说明这组码长刚好把整棵二叉树"装满",对应码字:

$$0,\ 10,\ 110,\ 111$$

如果某组码长使求和大于 1,例如 $(1,1,1)$,则

$$2^{-1}+2^{-1}+2^{-1}=\frac32>1$$

这说明二叉树容量不够,根本不可能构造出前缀码。

从"编码问题"到"优化问题"

Kraft 不等式的价值在于:它把"能否构造出这样的码"转写成了一个纯数学约束。于是最优压缩问题就变成:

$$\min \sum_i p_i l_i \quad \text{s.t.} \quad \sum_i D^{-l_i}\le 1,\ l_i\in\mathbb{Z}_{>0}$$

后面所有关于熵下界、最优码长、Huffman 码的结论,本质上都是在研究这个优化问题。

PDFKraft 不等式p.8
正在渲染 PDF 第 8 页…
Kraft 不等式(PDF 第 8 页) · 打开原文
PDF码树与 Kraft 不等式证明思路p.9
正在渲染 PDF 第 9 页…
码树与 Kraft 不等式证明思路(PDF 第 9 页) · 打开原文
5.3
最优码长为什么会指向熵

现在我们已经知道哪些码长可行,接下来要问:最优码长大概应该长成什么样?

先暂时忽略"码长必须是整数"这个离散限制,把优化问题放松成实数变量:

$$\min \sum_i p_i l_i \quad \text{s.t.} \quad \sum_i D^{-l_i}=1$$

为什么把不等式改成等式?因为如果严格小于 1,说明码树还有空余,还能继续缩短某些码字,期望长度就还能下降,所以最优点一定会把容量用满。

用拉格朗日乘子法,设

$$\mathcal{L}=\sum_i p_i l_i + \lambda\left(\sum_i D^{-l_i}-1\right)$$

$l_i$ 求偏导并令其为 0:

$$\frac{\partial \mathcal{L}}{\partial l_i}=p_i-\lambda (\ln D)D^{-l_i}=0$$

于是得到

$$D^{-l_i}\propto p_i \quad \Longrightarrow \quad l_i=-\log_D p_i$$

这就是最理想的码长分配。把它代回平均长度:

$$L^*=\sum_i p_i(-\log_D p_i)=H_D(X)$$

其中 $H_D(X)= -\sum_i p_i\log_D p_i = \frac{H(X)}{\log_2 D}$ 表示以 $D$ 为底度量的熵。

核心理解:熵不是凭空定义出来的神秘量,而是"最优可变长无损编码平均码长"在连续放松极限下自然出现的答案。

为什么现实里通常达不到精确等号

真实编码里每个码字长度必须是整数,所以理想值 $-\log_D p_i$ 往往无法直接实现。例如 $p_i=0.3$ 时,$-\log_2 0.3 \approx 1.737$ 比特,不可能真的分配 1.737 个比特。于是熵变成了一个理论下界。

压缩效率对比:三种码长的差距

用同一个概率分布来比较 Shannon 码、Huffman 码与熵的差距:

压缩效率对比:熵 vs Shannon 码 vs Huffman 码JSXGraph
压缩效率对比:熵 vs Shannon 码 vs Huffman 码

以概率分布 $(0.4, 0.3, 0.2, 0.1)$ 为例:Huffman 码长 $1.9$ bit,仅比熵 $1.846$ bit 高 $0.054$ bit;Shannon 码取上取整后为 $2.0$ bit,略逊一筹。

PDF最优码长与熵下界p.13
正在渲染 PDF 第 13 页…
最优码长与熵下界(PDF 第 13 页) · 打开原文
5.4
信源编码定理:熵是下界,而且可以逼近

信源编码定理(香农第一定理)

对于任意离散无记忆信源和任意 $D$ 元唯一可译码,其期望码长满足

$$L \ge H_D(X)$$

并且存在编码使得

$$H_D(X) \le L < H_D(X)+1$$

下界为什么成立

对任意唯一可译码,MacMillan 不等式说明 Kraft 约束仍然成立。令

$$q_i = \frac{D^{-l_i}}{\sum_j D^{-l_j}}$$

$q_i$ 是一个合法分布。将平均码长写成

$$L = \sum_i p_i l_i \ge -\sum_i p_i\log_D q_i$$

再利用相对熵非负性 $D(p\|q)=\sum_i p_i\log_D\frac{p_i}{q_i}\ge 0$,推出 $L\ge H_D(X)$

上界为什么成立

构造 Shannon 码,令 $l_i=\left\lceil \log_D \frac{1}{p_i} \right\rceil$。因为 $l_i \ge \log_D \frac1{p_i}$,所以 $D^{-l_i}\le p_i$,求和得 $\sum_i D^{-l_i}\le 1$,于是由 Kraft 不等式可构造出前缀码。另一方面,利用上取整不超过多加 1:

$$\log_D \frac1{p_i} \le l_i < \log_D \frac1{p_i}+1$$

乘上 $p_i$ 并求和得 $H_D(X) \le L < H_D(X)+1$

为什么分组编码能把"+1"磨掉

如果把 $n$ 个源符号打包成一个超级符号来编码,那么块熵变成 $H_D(X^n)=nH_D(X)$,而 Shannon 码给出的总块长只比它多不到 1。于是平均到每个原始符号:

$$H_D(X) \le \frac{L(X^n)}{n} < H_D(X)+\frac1n$$

$n\to\infty$ 时,额外损失 $1/n$ 消失。这就是"熵是可逼近的极限"的精确含义。

PDF香农第一定理p.15
正在渲染 PDF 第 15 页…
香农第一定理(PDF 第 15 页) · 打开原文
6.1
Shannon 码:最直接的近似最优构造

Shannon 码的思想非常朴素:既然理想码长是 $-\log_D p_i$,那就直接把它向上取整。

$$l_i=\left\lceil \log_D \frac{1}{p_i} \right\rceil$$

它的优点是:构造简单、理论分析干净、自动满足 $H_D(X) \le L < H_D(X)+1$。缺点是它只根据单个概率算码长,没有进一步优化码树结构,因此在逐符号编码里通常不如 Huffman 码短。

例:Shannon 码长怎么来

若概率分布为 $(0.4,0.3,0.2,0.1)$,则理想码长分别为

$(-\log_2 0.4, -\log_2 0.3, -\log_2 0.2, -\log_2 0.1) \approx (1.322, 1.737, 2.322, 3.322)$

向上取整后得到码长 $(2,2,3,4)$。它肯定可实现,但未必最优,因为高概率的第一个符号其实有机会只用 1 比特表示。

6.2
Huffman 编码:逐符号前缀码里的最优解

如果目标限定为逐符号、前缀、无损编码,那么 Huffman 编码给出了最优构造。它真正解决了这样一个问题:

在所有前缀码中,怎样让平均码长 $L$ 最小?

为什么"合并最小概率的两个符号"是对的

Huffman 算法背后有两个关键结构事实:

  1. 最优前缀码中,概率最小的两个符号一定可以放在最深层,且码长相同。
  2. 这两个最小概率符号的码字只在最后一位不同,因此可以先把它们视作一个"合并符号",概率是两者之和。

这样,原问题就递归地缩小成一个更小规模的最优编码问题。这正是 Huffman 贪心策略成立的根源。

算法步骤

  1. 把所有符号按概率放入最小堆
  2. 每次取出概率最小的两个节点,合并成一个新节点,概率为二者之和
  3. 重复直到只剩一个根节点
  4. 从根向叶回溯,左支赋 0,右支赋 1,即得码字

Huffman 合并树过程(文字流程图)

flowchart TD
    subgraph Step1["第1步:合并最小概率两个符号"]
        A1["d: 0.1"] & B1["c: 0.2"] --> C1["n₁: 0.3"]
    end
    subgraph Step2["第2步:再次合并最小概率两个节点"]
        A2["a: 0.4"] & B2["b: 0.3"] & C2["n₁: 0.3"] --> D2["n₁+b: 0.6"]
    end
    subgraph Step3["第3步:合并最后两个节点"]
        A3["a: 0.4"] & D3["n₂: 0.6"] --> ROOT["根节点 1.0"]
    end
    style A1 fill:#dbeafe,stroke:#2563eb
    style B1 fill:#dbeafe,stroke:#2563eb
    style C1 fill:#fef3c7,stroke:#d97706
    style D3 fill:#fef3c7,stroke:#d97706
    style ROOT fill:#dcfce7,stroke:#16a34a

Huffman 码满足 $H(X) \le L_{\text{Huffman}} < H(X)+1$,而且在所有二元逐符号前缀码中,它的期望长度最短。

PDFHuffman 编码p.24
正在渲染 PDF 第 24 页…
Huffman 编码(PDF 第 24 页) · 打开原文
例题 1
Huffman 编码构造与平均码长计算

Huffman 编码构造与平均码长计算

题目:设信源符号概率为 $p(a)=0.4,\ p(b)=0.3,\ p(c)=0.2,\ p(d)=0.1$。构造二元 Huffman 码,并计算平均码长与熵。

步骤 1:按概率从小到大合并

  1. 先合并 $d(0.1)$$c(0.2)$,得到新节点 $n_1(0.3)$
  2. 此时结点为 $a(0.4),\ b(0.3),\ n_1(0.3)$
  3. 再合并 $b(0.3)$$n_1(0.3)$,得到 $n_2(0.6)$
  4. 最后合并 $a(0.4)$$n_2(0.6)$ 得到根节点

步骤 2:回溯赋码(取左支为 0,右支为 1)

根
├── 左 → a: 码字 0(长度1)
└── 右 → n₂(0.6)
    ├── 左 → b: 码字 10(长度2)
    └── 右 → n₁(0.3)
        ├── 左 → c: 码字 110(长度3)
        └── 右 → d: 码字 111(长度3)
    
符号概率码字码长
$a$0.401
$b$0.3102
$c$0.21103
$d$0.11113

步骤 3:计算平均码长

$$L = 0.4\times 1 + 0.3\times 2 + 0.2\times 3 + 0.1\times 3 = 1.9\ \text{bit}$$

步骤 4:计算熵

$$H(X)= -0.4\log_2 0.4 -0.3\log_2 0.3 -0.2\log_2 0.2 -0.1\log_2 0.1 \approx 1.846\ \text{bit}$$

步骤 5:比较

$$L-H(X)\approx 1.9-1.846=0.054\ \text{bit}$$

这组 Huffman 码已经非常接近理论极限。

易错点
  • 合并的是最小概率两个,不是最大概率两个
  • 同概率时码字不唯一,但平均码长相同
  • Huffman 最优性只针对"逐符号前缀码",若允许长块联合编码,仍可能进一步逼近熵
PDFHuffman 例题p.25
正在渲染 PDF 第 25 页…
Huffman 例题(PDF 第 25 页) · 打开原文
6.3
Shannon-Fano-Elias 编码:从累计分布走向区间编码

Huffman 码按符号一个个赋离散码字。Shannon-Fano-Elias 编码则开始把注意力转向概率区间。它是理解算术编码的关键过渡。

核心思想:区间中点

先把符号按某个顺序排列,定义累计分布

$$F(x_i)=\sum_{j<i} p(x_j)$$

再定义修正后的中点累计量

$$\bar F(x_i)=F(x_i)+\frac12 p(x_i)$$

直觉上,$\bar F(x_i)$ 就是符号 $x_i$ 对应概率区间的中点。然后取码长

$$l(x_i)=\left\lceil \log_2 \frac1{p(x_i)} \right\rceil +1$$

并把 $\bar F(x_i)$ 的二进制展开前 $l(x_i)$ 位作为码字。

为什么区间中点能保证唯一译码

设符号 $x_i$ 的概率区间为 $[F(x_i),\ F(x_i)+p(x_i))$,其中点为 $\bar F(x_i)$。取前 $l(x_i)$ 位相当于在 $[0,1)$ 中选了一个长度为 $2^{-l(x_i)}$ 的小区间。由于 $l(x_i)$$\log_2 \frac1{p(x_i)}$ 多取了 1 位,所以这个小区间的宽度严格小于 $p(x_i)$,因此它完全落在符号 $x_i$ 自己的概率区间内部,不会碰到邻居区间。

所以不同符号的码字前缀区间互不相交,构成前缀码。

为什么额外多取 1 位

如果只取 $\lceil\log_2 \frac1{p_i}\rceil$ 位,截断误差可能导致二进制前缀恰好落在区间边界上,与邻居冲突。额外多取 1 位,相当于用宽度为 $2^{-l}$ 的小区间"盖住"区间中点,确保无论舍入规则如何,截断结果都落在该符号的概率区间内部。

Shannon-Fano-Elias 编码示例

题目:设概率分布为 $p(1)=0.25,\ p(2)=0.5,\ p(3)=0.125,\ p(4)=0.125$,构造 Shannon-Fano-Elias 码。

符号$p(x)$$F(x)$$\bar F(x)$(二进制)$l(x)$码字
10.2500.125 = 0.001₂3001
20.50.250.5 = 0.10₂210
30.1250.750.8125 = 0.1101₂41101
40.1250.8750.9375 = 0.1111₂41111

以符号 2 为例:中点是 $0.5=(0.1)_2$,取前 2 位便得到码字 10

平均码长满足 $L_{\text{SFE}} < H(X)+2$,比 Huffman 略松。

核心直觉:SFE 把"编码一个符号"变成了"在概率区间里选一个代表点"。这正是算术编码的思想前身——后者把这个过程从单符号扩展到了整条消息的嵌套区间。
PDFShannon-Fano-Elias 编码p.34
正在渲染 PDF 第 34 页…
Shannon-Fano-Elias 编码(PDF 第 34 页) · 打开原文
6.4
算术编码:对整条消息编码,而不是逐符号编码

Huffman 的瓶颈来自整数码长。即使某个符号理想码长是 1.37 bit,也只能给 1 bit 或 2 bit。算术编码绕开的办法是:

不再给每个符号单独分配一个码字,而是把整条消息映射成区间 $[0,1)$ 中的一个实数。消息越长,区间越窄,需要写出的二进制位数越精确,但平均到每个符号上就越接近熵。

基本过程

  1. 先按符号概率把 $[0,1)$ 划分成若干子区间
  2. 读入第一个符号后,保留其对应子区间
  3. 再在这个子区间内按同样比例继续细分,对第二个符号选区间
  4. 不断递归,最终整条消息对应一个极小区间
  5. 输出该区间内任意一个二进制小数即可唯一表示整条消息

算术编码区间递归细分

$p(A)=0.6,\ p(B)=0.4$,初始区间 $[0,1)$。消息 BA 的编码过程:

算术编码区间递归细分(消息 BA)JSXGraph
算术编码区间递归细分(消息 BA)

每读入一个符号,就在当前区间内部按概率比例再次切分。最终消息 BA 对应区间 $[0.6,0.84)$,输出该区间内任一数(如 $0.75$)即可代表整条消息。

关键性质

  • 消息越长,平均码率越接近熵 $H(X)$,因为额外开销(起始区间固定长度)被分摊到更多符号上。
  • 能突破逐符号整数码长带来的浪费,在 JPEG、JPEG2000、H.264/AVC 等压缩系统中广泛使用。
  • 实现复杂度比 Huffman 高,需要数值稳定处理以防止区间溢出。

课件中的 Python 实现

import collections

class ArithmeticCoder:
    def encode(self, data):
        freq = collections.Counter(data)
        total = len(data)

        prob_table = {}
        cum = 0.0
        for s in sorted(freq):
            p = freq[s] / total
            prob_table[s] = (cum, cum + p)
            cum += p

        low, high = 0.0, 1.0
        for s in data:
            rng = high - low
            lo, hi = prob_table[s]
            low, high = low + rng * lo, low + rng * hi

        return (low + high) / 2, prob_table, len(data)

每读取一个符号,就在当前区间内部按概率再次切分,最后返回区间中点作为编码结果。

PDF算术编码p.36
正在渲染 PDF 第 36 页…
算术编码(PDF 第 36 页) · 打开原文
例题 2
什么时候 Huffman 能刚好达到熵

Huffman 码达到熵下界的条件

题目:设三元信源满足 $p(a)=0.5,\ p(b)=0.25,\ p(c)=0.25$,构造 Huffman 码,并判断是否达到熵下界。

解答

一组 Huffman 码可取

$a\to 0,\quad b\to 10,\quad c\to 11$

平均码长为

$$L=0.5\times 1+0.25\times 2+0.25\times 2=1.5\ \text{bit}$$

熵为

$$H(X)= -0.5\log_2 0.5 -0.25\log_2 0.25 -0.25\log_2 0.25 = 1.5\ \text{bit}$$

因此 $L=H(X)$,恰好达到理论下界。

为什么这次能取等

因为这组概率恰好是二进制概率:

$$0.5=2^{-1},\quad 0.25=2^{-2},\quad 0.25=2^{-2}$$

理想码长 $-\log_2 p_i$ 本身就是整数 $(1,2,2)$,整数约束没有造成额外损失。

结论:当所有符号概率恰好是 $D$ 的负整数次幂(即 $p_i = D^{-l_i^*}$,其中 $l_i^*$ 为整数)时,Huffman 码可以达到精确的熵下界。
6.5
四种编码方法对比
方法核心思想平均码长界优点局限
Shannon 码直接取 $\lceil -\log p_i \rceil$$H \le L < H+1$构造简单,理论清楚通常不最优
Huffman 码递归合并最小概率符号$H \le L < H+1$逐符号前缀码最优仍受整数码长限制
Shannon-Fano-Elias取累计概率区间中点前缀$L < H+2$思想上通往区间编码性能一般不如 Huffman
算术编码整条消息映射到一个概率区间可任意逼近 $H$压缩率高,接近极限实现更复杂,需数值稳定处理
6.6
香农码 vs Huffman 码:单符号层面的差异

从理论上讲,Huffman 码在期望意义上优于 Shannon 码,但两者差距不超过 1 比特。然而对于某些特定符号,Shannon 码反而可能给出更短的码字。

Shannon 码 vs Huffman 码的单符号码长对比

符号概率 $p(x)$Shannon 码长 $\lceil -\log_2 p(x) \rceil$Huffman 码长
11/321
21/322
31/433
41/1233

在这个例子中,Huffman 码平均更短(因为高概率符号 1 只用了 1 比特),但 Shannon 码的码字结构更规则、更可预测。

复习速查

  • Kraft 不等式:前缀码存在充要条件 $\sum D^{-l_i}\le 1$;几何含义是码树容量不溢出。
  • 熵下界$L\ge H_D(X)$,理想码长 $l_i^*=-\log_D p_i$,此时 $L=H_D(X)$
  • 信源编码定理$H_D(X)\le L < H_D(X)+1$(单符号),$H_D(X)\le L_n < H_D(X)+\varepsilon$(分组编码,$n\to\infty$)。
  • Huffman:递归合并最小概率两个节点;最优逐符号前缀码;满足 $H(X)\le L_H < H(X)+1$
  • Shannon-Fano-Elias:取累计概率区间中点的二进制前缀;界 $L<H(X)+2$;关键贡献是"区间代表点"思想。
  • 算术编码:整条消息对应 $[0,1)$ 中的嵌套子区间;可任意逼近熵;突破整数码长限制。
  • 何时达到精确等号:当所有 $p_i=D^{-l_i}$$l_i$ 为整数)时。

参考来源

  • 课程课件《第五章&第六章》:Kraft 不等式、香农第一定理、Huffman 编码、Shannon-Fano-Elias 编码、算术编码
  • Georgia Tech ECE587 课程页面:Lecture 7-10 覆盖 source coding、Huffman、Shannon-Fano-Elias 与 arithmetic coding
  • UMD ENEE627 课程页面:Lecture 7-11 覆盖 data compression、Kraft inequality、optimal prefix codes、Huffman 与 Shannon-Fano-Elias
  • Cover & Thomas, Elements of Information Theory, Chapter 5