理解和使用zlib库
作者: 阙荣文
日期: 2016.6.2
日期: 2016.6.2
0. 很多年以前我曾经写过一篇文章(http://blog.csdn.net/querw/article/details/1452041)简单介绍 zlib 的使用方法,老实说当时自己都不是很明白 zlib 是怎么回事,现在想起来那个时候年轻嘛,胆子大,脸皮厚...希望用一篇新的文章纪念少不更事的无知.
1. deflate算法, zlib 格式, gzip 格式
本文并不是一篇介绍压缩算法的文章,请读者自行查阅关于 LZ77 算法的详情.deflate 是 LZ77 算法的一个增强版,对各种数据提供无损压缩,是 zlib 目前唯一实现的压缩算法.
一段数据经过 deflate 算法压缩之后形成一段输出数据,这段输出数据就是纯粹的压缩数据,没有任何额外信息如长度,校验和等.可以直接存储或者在网络中传输原始压缩数据并由 inflate 算法解压缩,但是用户要保证数据的完整性.
当然,我们也可以为这段原始数据额外添加一个 zlib 格式(rfc1950)的数据头/尾,使用 adler32 校验和,定义如下:
+---+---+
|CMF|FLG| (more-->)
+---+---+
(if FLG.FDICT set)
+-----+-----+-----+-----+
| DICTID | (more-->)
+-----+-----+-----+-----+
+========================+----+-----+-----+----+
| ...compressed data... | ADLER32 |
+========================+----+-----+-----+----+
本文并不是一篇介绍压缩算法的文章,请读者自行查阅关于 LZ77 算法的详情.deflate 是 LZ77 算法的一个增强版,对各种数据提供无损压缩,是 zlib 目前唯一实现的压缩算法.
一段数据经过 deflate 算法压缩之后形成一段输出数据,这段输出数据就是纯粹的压缩数据,没有任何额外信息如长度,校验和等.可以直接存储或者在网络中传输原始压缩数据并由 inflate 算法解压缩,但是用户要保证数据的完整性.
当然,我们也可以为这段原始数据额外添加一个 zlib 格式(rfc1950)的数据头/尾,使用 adler32 校验和,定义如下:
+---+---+
|CMF|FLG| (more-->)
+---+---+
(if FLG.FDICT set)
+-----+-----+-----+-----+
| DICTID | (more-->)
+-----+-----+-----+-----+
+========================+----+-----+-----+----+
| ...compressed data... | ADLER32 |
+========================+----+-----+-----+----+
2个字节的 zlib 头, 4个字节的字典(可选), deflate 原始压缩数据, 4个字节的 adler32 校验和. 这是一种非常简洁的数据包装格式.
gzip(rfc1952) 是不同于 zlib 的另外一种格式的数据头/尾,使用 CRC32 校验和,定义如下:
+---+---+---+---+---+---+---+---+---+---+
|ID1|ID2|CM |FLG| MTIME |XFL|OS | (more-->)
+---+---+---+---+---+---+---+---+---+---+
|ID1|ID2|CM |FLG| MTIME |XFL|OS | (more-->)
+---+---+---+---+---+---+---+---+---+---+
(if FLG.FEXTRA set)
+---+---+=================================+
| XLEN |...XLEN bytes of "extra field"...| (more-->)
+---+---+=================================+
| XLEN |...XLEN bytes of "extra field"...| (more-->)
+---+---+=================================+
(if FLG.FNAME set)
+=========================================+
|...original file name, zero-terminated...| (more-->)
+=========================================+
|...original file name, zero-terminated...| (more-->)
+=========================================+
(if FLG.FCOMMENT set)
+===================================+
|...file comment, zero-terminated...| (more-->)
+========&
|...file comment, zero-terminated...| (more-->)
+========&