zstd 简介
维基百科定义:
Zstandard(或Zstd)是由Facebook的Yann Collet开发的一个无损数据压缩算法。该名称也指其C语言的参考实现。第1版的实现于2016年8月31日发布为自由软件
设计Zstandard的目的是提供一个类似于DEFLATE算法的压缩比,但更快,特别是解压缩快的算法。
它的压缩级别从负5级(最快)到22级(压缩速度最慢,但是压缩比最高)可以调节。
zstd包里面有压缩和解压缩的并行(多线程)实现。从1.3.2版本2017年10月)开始,zstd 有选择地实现非常长的搜索和重复数据消除(–long,128MiB窗口),类似于rzip或lrzip。
压缩速度在最快和最慢级别之间可以相差20倍或更多,而解压缩速度统统很快,在最快和最慢级别之间相差不到20%。
Zstandard命令行有一个“自适应”(–adapt)模式,根据I/O条件改变压缩级别,主要是写入输出的速度。
Zstd在其最大压缩级别下的压缩比接近lzma、lzham和ppmx,并且比lza或bzip2性能更好。
Zstandard达到了当前的Pareto边界,因为它解压缩的速度比任何其他当前可用的算法都要快,并且有类似的或者更好的压缩比。
字典对小文件的压缩比有很大的影响,所以Zstandard可以使用用户提供的压缩字典。它还提供了一种训练模式,能够从一组样本生成一个字典。
特别是,可以加载一个字典来处理文件之间具有冗余的大型文件集,但不一定在每个文件(例如日志文件)内。
c++中应用
最常见的就是对于字符串的压缩,下边给出字符串源码
转载请注明出处,谢谢
欢迎访问我的github https://github.com/hashyong/zstd_util
//
// -*- coding: utf-8-unix; -*-
// Copyright c) 2020 Tencent, Inc.
// All rights reserved.
//
// Date: 2020/11/30 13:45
// File: zstd.cc
// Desc:
//
#include "util.h"
#include "third_party/zstd/zstd.h"
namespace util {
int Util::CompressStringconst string& src, string& dst, int compressionlevel) {
size_t const cBuffSize = ZSTD_compressBoundsrc.size));
dst.resizecBuffSize);
auto dstp = const_cast<void*>static_cast<const void*>dst.c_str)));
auto srcp = static_cast<const void*>src.c_str));
size_t const cSize = ZSTD_compressdstp, cBuffSize, srcp, src.size), compressionlevel);
auto code = ZSTD_isErrorcSize);
if code) {
return code;
}
dst.resizecSize);
return code;
}
int Util::DecompressStringconst string& src, string& dst) {
size_t const cBuffSize = ZSTD_getFrameContentSizesrc.c_str), src.size));
if 0 == cBuffSize) {
return cBuffSize;
}
if ZSTD_CONTENTSIZE_UNKNOWN == cBuffSize) {
return StreamDecompressStringsrc, dst);
}
if ZSTD_CONTENTSIZE_ERROR == cBuffSize) {
return -2;
}
dst.resizecBuffSize);
auto dstp = const_cast<void*>static_cast<const void*>dst.c_str)));
auto srcp = static_cast<const void*>src.c_str));
size_t const cSize = ZSTD_decompressdstp, cBuffSize, srcp, src.size));
auto code = ZSTD_isErrorcSize);
if code) {
return code;
}
dst.resizecSize);
return code;
}
int Util::StreamCompressStringconst string& src, string& dst, int compressionlevel) {
size_t const buffInSize = ZSTD_CStreamInSize);
string buffInTmp;
buffInTmp.reservebuffInSize);
auto buffIn = const_cast<void*>static_cast<const void*>buffInTmp.c_str)));
auto buffOutSize = ZSTD_CStreamOutSize);
string buffOutTmp;
buffOutTmp.reservebuffOutSize);
auto buffOut = const_cast<void*>static_cast<const void*>buffOutTmp.c_str)));
ZSTD_CCtx* const cctx = ZSTD_createCCtx);
ZSTD_CCtx_setParametercctx, ZSTD_c_compressionLevel, compressionlevel);
size_t const toRead = buffInSize;
auto local_pos = 0;
auto buff_tmp = const_cast<char*>buffInTmp.c_str));
for ;;) {
size_t read = src.copybuff_tmp, toRead, local_pos);
local_pos += read;
int const lastChunk = read < toRead);
ZSTD_EndDirective const mode = lastChunk ? ZSTD_e_end : ZSTD_e_continue;
ZSTD_inBuffer input = {buffIn, read, 0};
int finished;
do {
ZSTD_outBuffer output = {buffOut, buffOutSize, 0};
size_t const remaining = ZSTD_compressStream2cctx, &output, &input, mode);
dst.insertdst.end), buffOutTmp.begin), buffOutTmp.begin) + output.pos);
finished = lastChunk ? remaining == 0) : input.pos == input.size);
} while !finished);
if lastChunk) {
break;
}
}
ZSTD_freeCCtxcctx);
return 0;
}
int Util::StreamDecompressStringconst string& src, string& dst, int compressionlevel) {
size_t const buffInSize = ZSTD_DStreamInSize);
string buffInTmp;
buffInTmp.reservebuffInSize);
auto buffIn = const_cast<void*>static_cast<const void*>buffInTmp.c_str)));
auto buffOutSize = ZSTD_DStreamOutSize);
string buffOutTmp;
buffOutTmp.reservebuffOutSize);
auto buffOut = const_cast<void*>static_cast<const void*>buffOutTmp.c_str)));
ZSTD_DCtx* const dctx = ZSTD_createDCtx);
size_t const toRead = buffInSize;
size_t read;
size_t last_ret = 0;
size_t local_pos = 0;
auto buff_tmp = const_cast<char*>buffInTmp.c_str));
while read = src.copybuff_tmp, toRead, local_pos))) {
local_pos += read;
ZSTD_inBuffer input = {buffIn, read, 0};
while input.pos < input.size) {
ZSTD_outBuffer output = {buffOut, buffOutSize, 0};
size_t const ret = ZSTD_decompressStreamdctx, &output, &input);
dst.insertdst.end), buffOutTmp.begin), buffOutTmp.begin) + output.pos);
last_ret = ret;
}
}
ZSTD_freeDCtxdctx);
iflast_ret != 0) {
return -3;
}
return 0;
}
} // namespace util
作者:
fattycoder
出处:
https://www.cnblogs.com/fattyCoder/
关于作者:挺喜欢写代码的
本文版权归作者所有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出,
原文链接
如有问题, 可邮件(564790073@qq.com)咨询.
