gpt4 book ai didi

c++ - 如何使用 boost iostreams 进行流式解压缩

转载 作者:搜寻专家 更新时间:2023-10-31 01:31:52 27 4
gpt4 key购买 nike

我正在使用 boost iostreams (1.64.0) 来解压缩 zlib 数据。我想做流式解压。这意味着压缩数据的大小不可预测。我写了下面的代码示例。

#include <sstream>
#include <string>
#include <iostream>

#include <boost/iostreams/filtering_streambuf.hpp>
#include <boost/iostreams/copy.hpp>
#include <boost/iostreams/filter/zlib.hpp>

int main() {
// Compress
std::stringstream sender;
boost::iostreams::filtering_streambuf<boost::iostreams::input> out;
out.push(boost::iostreams::zlib_compressor());
out.push(sender);
sender << "Hello World";
std::stringstream compressed;
boost::iostreams::copy(out, compressed);

// Decompress
boost::iostreams::filtering_streambuf<boost::iostreams::input> in;
in.push(boost::iostreams::zlib_decompressor());
in.push(compressed);
std::istream is(&in);
std::size_t const buf_size = 256;
char buf[buf_size] = { '\0' };
#if 0
is.getline(buf, buf_size); // works fine
#else
std::size_t read_size = is.readsome(buf, buf_size);
std::cout << "read_size:" << read_size << std::endl;
#endif
// http://www.cplusplus.com/reference/ios/ios/rdstate/
std::cout << "rdstate:" << is.rdstate() << std::endl;
std::cout << buf << std::endl;

}

我使用 readsome() 因为数据的大小是不可预测的。我得到以下输出:

read_size:0
rdstate:0

这对我来说是出乎意料的。

如果我使用 getline() 而不是 readsome(),我得到以下输出:

rdstate:2
Hello World

这是预期的输出。

我认为当我使用 readsome() 时,输出应该是相同的。我无法在实际代码中使用 getline() 我的,因为原始数据是二进制格式。

有什么方法可以将 readsome()filtering_streambuf 一起使用,或者有什么好的方法可以流式解压缩不可预测长度的二进制数据吗?

最佳答案

感谢sehe's comment ,问题就解决了。

我写了the response对于评论,但很难阅读,因为代码格式不正确。所以我自己回答。我希望它能帮助其他有类似问题的人。

我换了

std::size_t read_size = is.readsome(buf, buf_size);

is.read(buf, buf_size);
std::size_t read_size = is.gcount();

,那么问题就解决了。

我误解了 std::istream::read block 直到读取 buf_size 长度数据。这不是真的。即使实际读取大小小于 buf_size,函数也会返回。参见 http://www.cplusplus.com/reference/istream/istream/read/ .为了获得 read_size,我调用了 std::istream::gcount()。参见 http://www.cplusplus.com/reference/istream/istream/gcount/ .

注意:我对 boost::asio::read 感到困惑和 boost::asio::ip::tcp::socket::read_some .但它们的行为不同于 std::istream 的行为。

修复版的完整代码如下:

#include <sstream>
#include <string>
#include <iostream>

#include <boost/iostreams/filtering_streambuf.hpp>
#include <boost/iostreams/copy.hpp>
#include <boost/iostreams/filter/zlib.hpp>

int main() {
// Compress
std::stringstream sender;
boost::iostreams::filtering_streambuf<boost::iostreams::input> out;
out.push(boost::iostreams::zlib_compressor());
out.push(sender);
sender << "Hello World";
std::stringstream compressed;
boost::iostreams::copy(out, compressed);

// Decompress
boost::iostreams::filtering_streambuf<boost::iostreams::input> in;
in.push(boost::iostreams::zlib_decompressor());
in.push(compressed);
std::istream is(&in);
std::size_t const buf_size = 256;
char buf[buf_size] = { '\0' };
is.read(buf, buf_size);
std::size_t read_size = is.gcount();
std::cout << "read_size:" << read_size << std::endl;
// http://www.cplusplus.com/reference/ios/ios/rdstate/
std::cout << "rdstate:" << is.rdstate() << std::endl;
std::cout << buf << std::endl;

}

关于c++ - 如何使用 boost iostreams 进行流式解压缩,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44680590/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com