字节buffer数据的数据压缩算法法


基于统计的数据压缩编码比如Huffman編码,需要得到先验知识——信源的字符频率然后进行压缩。但是在大多数情况下这种先验知识是很难预先获得。因此设计一种更為通用的数据压缩编码显得尤为重要。LZ77数据数据压缩算法法应运而生其核心思想:利用数据的重复结构信息来进行数据压缩。举个简单嘚例子比如

取之以仁义,守之以仁义者周也。取之以诈力守之以诈力者,秦也

取之以仁义守之以诈力均偅复出现过,只需指出其之前出现的位置便可表示这些词。为了指明出现位置我们定义一个相对位置,如图

相对位置之后的消息串为取之以诈力守之以诈力者,秦也,若能匹配相对位置之前的消息串则编码为以其匹配的消息串的起始与末端index;若未能匹配上,则以原字符编码相对位置之后的消息串可编码为:[(1-3),(诈力),(6),(7-9),(诈力),(12),(6),(秦),(15-16)],如图所示:

上面的例子展示如何利用索引值来表示词以达到数据压缩的目嘚。LZ77算法的核心思想亦是如此其具体的压缩过程不过比上述例子稍显复杂而已。

本文讲主要讨论LZ77算法如何做压缩及解压缩关于LZ77算法的唯一可译、无损压缩(即解压可以不丢失地还原信息)的性质,其数学证明参看原论文[1]

至于如何描述重复结构信息,LZ77算法给出叻更为确切的数学解释首先,定义字符串\(S\)的长度为\(N\)字符串\(S\)的子串\(S_{i,j},\ 1\le i,j \le

定义\(p^j\)为所有情况下的最长匹配\(i\)值,即

extension)LZ77算法的核心思想便源于此——用历史出现过的字符串做词典,编码未来出现的字符以达到数据压缩的目的。在具体实现中用滑动窗口(Sliding Window)字典存储历史字符,Lookahead Buffer存储待压缩的字符Cursor作为两者之间的分隔,如图所示:

  • \(p\)表示最长匹配时字典中字符开始时的位置(相对于Cursor位置),
  • \(l\)为最长匹配字符串的长度

压缩的过程,就是重复输出\((p,l,c)\)并将Cursor移动至\(l+1\),伪代码如下:

为了能保证正确解码解压缩时的滑动窗口长度与压缩时一样。在解压缩遇到\((p,l,c)\)大致分为三类情况:

  • \(p<l\),即出现循环编码需要从左至右循环拼接,伪代码如下:

bitarray的实现请参看下面给出简单的python实现。

我要回帖

更多关于 数据压缩算法 的文章

 

随机推荐