|
zlib是一套公开源代码的压缩,解压缩的函数库,提供了很多文件操作的方法,但是他不是一套类库,所以有兴趣的人都可以把他进行封装,实现自己的类库,和更高层的接口。
具体的介绍可以参考http://www.gzip.org/zlib/主页,这里有详细介绍。 这里简单实现了zlib的最简单的用法,压缩一个文件,通过使用文件映射来实现的。 HANDLE hFile, hFileToWrite; HANDLE hMapFile, hMapFileToWrite; //创建一个文件映射 LPVOID lpMapAddress, lpMapAddressToWrite; //创建一个文件映射的视图用来作为source ////////////////////////////////////////////////////////////////////////////////// //以下是创建一个文件,用来保存压缩后的文件 if (hFileToWrite == INVALID_HANDLE_VALUE) hMapFileToWrite = CreateFileMapping(hFileToWrite, // Current file handle. lpMapAddressToWrite = MapViewOfFile(hMapFileToWrite, // Handle to mapping object. //这里是将压缩前的大小保存在文件的第一个DWORD里面
//这里就是最重要的,zlib里面提供的一个方法,将源缓存的数据压缩至目的缓存 ////////////////////////////////////////////////////////////////////// UnmapViewOfFile(lpMapAddress); UnmapViewOfFile(lpMapAddressToWrite); 解压缩的方法其他地方都一样,不同的就是使用方法是uncompress而不是compress
------------------------------------------------------------------------------------------------------------------------------
zlib 是通用的压缩库,提供了一套 in-memory 压缩和解压函数,并能检测解压出来的数据的完整性(integrity)。zlib 也支持读写 gzip (.gz) 格式的文件。下面介绍两个最有用的函数——compress 和 uncompress。 int compress(Bytef *dest, uLongf *destLen, const Bytef *source, uLong sourceLen); compress函数将 source 缓冲区中的内容压缩到 dest 缓冲区。 sourceLen 表示source 缓冲区的大小(以字节计)。注意函数的第二个参数 destLen 是传址调用。当调用函数时,destLen表示 dest 缓冲区的大小,destLen > (sourceLen + 12)*100.1%。当函数退出后,destLen 表示压缩后缓冲区的实际大小。此时 destLen /sourceLen 正好是压缩率。 compress 若成功,则返回 Z_OK;若没有足够内存,则返回 Z_MEM_ERROR;若输出缓冲区不够大,则返回 Z_BUF_ERROR。 int uncompress(Bytef *dest, uLongf *destLen, const Bytef *source, uLong sourceLen); uncompress 函数将 source 缓冲区的内容解压缩到 dest 缓冲区。sourceLen 是source 缓冲区的大小(以字节计)。注意函数的第二个参数 destLen 是传址调用。当调用函数时,destLen 表示 dest 缓冲区的大小, dest 缓冲区要足以容下解压后的数据。在进行解压缩时,需要提前知道被压缩的数据解压出来会有多大。这就要求在进行压缩之前,保存原始数据的大小(也就是解压后的数据的大小)。这不是 zlib 函数库的功能,需要我们做额外的工作。当函数退出后, destLen 是解压出来的数据的实际大小。 uncompress 若成功,则返回 Z_OK ;若没有足够内存,则返回 Z_MEM_ERROR;若输出缓冲区不够大,则返回 Z_BUF_ERROR。若输入数据有误,则返回 Z_DATA_ERROR。 zlib 带的 example.c 是个很好的学习范例,值得一观。我们写个程序,验证 zlib 的压缩功能。所写的测试程序保存为 testzlib.cpp ,放在 zlib-1.1.4 目录下。程序源代码: // testzlib.cpp 简单测试 zlib 的压缩功能 #include <cstring> #include <cstdlib> #include <iostream> #include "zlib.h" using namespace std; int main() { int err; Byte compr[200], uncompr[200]; // big enough uLong comprLen, uncomprLen; const char* hello = "12345678901234567890123456789012345678901234567890"; uLong len = strlen(hello) + 1; comprLen = sizeof(compr) / sizeof(compr[0]); err = compress(compr, &comprLen, (const Bytef*)hello, len); if (err != Z_OK) { cerr << "compess error: " << err << '/n'; exit(1); } cout << "orignal size: " << len << " , compressed size : " << comprLen << '/n'; strcpy((char*)uncompr, "garbage"); err = uncompress(uncompr, &uncomprLen, compr, comprLen); if (err != Z_OK) { cerr << "uncompess error: " << err << '/n'; exit(1); } cout << "orignal size: " << len << " , uncompressed size : " << uncomprLen << '/n'; if (strcmp((char*)uncompr, hello)) { cerr << "BAD uncompress!!!/n"; exit(1); } else { cout << "uncompress() succeed: /n" << (char *)uncompr; } } 编译执行这个程序,输出应该是 D:/libpng/zlib-1.1.4>bcc32 testzlib.cpp zlib.lib D:/libpng/zlib-1.1.4>testzlib orignal size: 51 , compressed size : 22 orignal size: 51 , uncompressed size : 51 uncompress() succeed: 12345678901234567890123456789012345678901234567890 |
本文介绍了zlib压缩库的基本用法,包括压缩和解压缩文件的过程,并通过一个简单的示例展示了如何使用compress和uncompress函数进行数据的压缩与还原。
290

被折叠的 条评论
为什么被折叠?



