需要有关如何使用霍夫曼代码对单词进行编码的帮助

3 compression algorithm encoding huffman-code

你如何使用诸如 NEED 之类的霍夫曼代码对单词进行编码

pax*_*blo 5

霍夫曼编码基本上使用可变长度的位串来表示标记(通常是有几个例外的字符)。令牌越常见,它的位长度就越短,并且在处理流时这(通常)是动态的。

通常有两种特殊的令牌,ESCAPE 和 END-STREAM。

Encoding 维护一个字典,它基本上是查找位序列以获取令牌。最初它只包含两个特殊标记。

ESCAPE 和 END_STREAM 的初始位序列可能是 0 和 1(这在开始时并不重要)。当编码器接收到不在字典中的字符时,它输出 ESCAPE 和全长令牌,然后添加它并根据所有令牌的频率分配新的位序列。

所以你的 'N' 可能会导致输出流:

0 xxxxxxxx
| +- token code for N
+--- ESCAPE
Run Code Online (Sandbox Code Playgroud)

和新词典:

ESCAPE:00
END-STREAM:01
N:1
Run Code Online (Sandbox Code Playgroud)

那么你的“E”可能会导致输出流:

0 xxxxxxxx 0 yyyyyyyy
             +- token code for E
Run Code Online (Sandbox Code Playgroud)

和新词典:

ESCAPE:00
END-STREAM:01
N:10
E:11
Run Code Online (Sandbox Code Playgroud)

您的下一个 E 不会导致 ESCAPE 输出,因为它已经在字典中,所以您只需输出其代码 (11)。它会改变字典,因为 E 现在有更高的计数。这在我们的情况下无关紧要,因为所有字符都是两个二进制数字,但在更复杂的示例中,“E”标记的位长度会缩短。

当 D 到达时,输出流变为:

0 xxxxxxxx 0 yyyyyyyy 11 0 zzzzzzzz
                      |    +- token code for D
                      +------ second E
Run Code Online (Sandbox Code Playgroud)

和新词典:

ESCAPE:00
END-STREAM:011
N:010
E:11
D:10
Run Code Online (Sandbox Code Playgroud)

所以你可以看到,随着更多字符的进入,常见字符的位长度减少,不常见字符的位长度增加,从而为您提供压缩。在这种情况下,N(或 D)获得 3 位代码,而 E 坚持使用 2 位代码,因为它们更多。

美妙之处在于您不需要将字典与文件一起存储,因为 ESCAPE 部分也会动态构建它以进行解压缩。

此外,因为直到最后都没有 END-STREAM 令牌,所以它的位长不断变大。与 ESCAPE 类似,虽然仍然有很多新角色进入,但它的位长度保持较短,但是,当没有新角色到来时,它会遭受与 END-STREAM 相同的命运。

对于(8 位 ASCII)输入流来说,最好的情况是一个只包含数百万个相同字符的文件。第一个字符花费 9 位,然后每个附加字符花费 1 位,然后流结束花费 2 位。这种快速接近 1 比 8 的压缩率 (97.5%)。

最坏的情况是每个字符中的一个,每个字符花费 9 位加上流的结尾——这实际上将流扩展了 12.5%。