为什么需要销毁使用 boost::iostreams::zlib_compressor 的 boost::iostream::filtering_ostream 才能写入接收器?

Why boost::iostream::filtering_ostream using boost::iostreams::zlib_compressor needs to be destroyed for the sink to be written?

提问人:matovitch 提问时间:3/22/2019 最后编辑:matovitch 更新时间:12/25/2022 访问量:1390

问:

在今天花了相当多的时间调试问题之后,我注意到需要销毁才能写入接收器。boost::iostream::filtering_ostream

测试代码:

#include <boost/iostreams/filtering_stream.hpp>
#include <boost/iostreams/filter/zlib.hpp>

#include <sstream>

struct ZlibOstream : boost::iostreams::filtering_ostream
{
    ZlibOstream(std::ostream& os)
    {
        boost::iostreams::filtering_ostream::push(boost::iostreams::zlib_compressor{});
        boost::iostreams::filtering_ostream::push(os);
    }
};

int main()
{   
    std::ostringstream oss;
    
    #ifdef HAS_SCOPE
    {
    #endif
    
    ZlibOstream zlibOstream{oss};
    
    zlibOstream << "This is a test string.\n";
    
    #ifdef HAS_SCOPE
    }
    #endif
    
    return (oss.tellp() == 0);
}

调用不起作用,当我删除 .flush()zlib_compressor

大肠杆菌的结果:https://coliru.stacked-crooked.com/a/7cd166d2d820e838

这种行为背后的原因是什么?

C++ 提升 IOSTREAM

评论


答:

1赞 matovitch 3/22/2019 #1

这实际上与这个问题有关:

刷新 boost::iostreams::zlib_compressor。如何获得“同步刷新”?

您需要调用才能进行刷新。boost::iostreams::zlib_compressor::close

您可以通过调用 或 .pop()reset()boost::iostream::filtering_ostream

请注意,顾名思义,弹出链中的最后一个过滤器并完全清除链,以便之后无法使用。pop()reset()filtering_ostream

例:

#include <boost/iostreams/filtering_stream.hpp>
#include <boost/iostreams/filter/zlib.hpp>

#include <sstream>

struct ZlibOstream : boost::iostreams::filtering_ostream
{
    ZlibOstream(std::ostream& os)
    {
        boost::iostreams::filtering_ostream::push(boost::iostreams::zlib_compressor{});
        boost::iostreams::filtering_ostream::push(os);
    }
};

int main()
{   
    std::ostringstream oss;

    ZlibOstream zlibOstream{oss};

    zlibOstream << "This is a test string.\n";

    zlibOstream.reset(); // needed if you want to write to oss

    return oss.tellp();
}

评论

1赞 OwnageIsMagic 5/18/2020
有免费功能boost::iostreams::close