2016-08-16 67 views
1

我有一组压缩文件。我必须解压缩所有文件并创建一个大文件。下面的代码工作正常,但我不想使用std :: stringstream,因为文件很大,我不想创建文件内容的中间副本。使用boost将多个文件解压到单个文件中

如果我试图直接使用boost::iostreams::copy(inbuf, tempfile);,它会自动关闭文件(tmpfile)。有没有更好的方法来复制内容?或者至少,我可以避免自动关闭此文件?

std::ofstream tempfile("/tmp/extmpfile", std::ios::binary); 
for (set<std::string>::iterator it = files.begin(); it != files.end(); ++it) 
{ 
    string filename(*it); 
    std::ifstream gzfile(filename.c_str(), std::ios::binary); 

    boost::iostreams::filtering_streambuf<boost::iostreams::input> inbuf; 
    inbuf.push(boost::iostreams::gzip_decompressor()); 
    inbuf.push(gzfile); 

    //closes tempfile automatically!! 
    //boost::iostreams::copy(inbuf, tempfile); 

    std::stringstream out; 
    boost::iostreams::copy(inbuf, out); 
    tempfile << out.str(); 
} 
tempfile.close(); 
+0

在目标文件的顶部使用一个简单的输出过滤器? –

回答

1

我知道有办法让Boost IOStreams知道它不应该关闭流。我想这需要你使用boost::iostream::stream<>而不是std::ostream

我看起来工作简单的解决方法是使用与单个std::filebuf对象相关联的临时std::ostream

#include <boost/iostreams/stream.hpp> 
#include <boost/iostreams/copy.hpp> 
#include <boost/iostreams/filtering_streambuf.hpp> 
#include <boost/iostreams/filter/gzip.hpp> 
#include <set> 
#include <string> 
#include <iostream> 
#include <fstream> 

int main() { 
    std::filebuf tempfilebuf; 
    tempfilebuf.open("/tmp/extmpfile", std::ios::binary|std::ios::out); 

    std::set<std::string> files { "a.gz", "b.gz" }; 
    for (std::set<std::string>::iterator it = files.begin(); it != files.end(); ++it) 
    { 
     std::string filename(*it); 
     std::ifstream gzfile(filename.c_str(), std::ios::binary); 

     boost::iostreams::filtering_streambuf<boost::iostreams::input> inbuf; 
     inbuf.push(boost::iostreams::gzip_decompressor()); 
     inbuf.push(gzfile); 

     std::ostream tempfile(&tempfilebuf); 
     boost::iostreams::copy(inbuf, tempfile); 
    } 
    tempfilebuf.close(); 
} 

Live On Coliru

随着样本数据等

echo a > a 
echo b > b 
gzip a b 

Gen erates extmpfile containing

a 
b 
相关问题