私はBoostシリアル化ライブラリを使用してきましたが、これは実際には非常に優れており、次のように、シリアル化可能なオブジェクトを文字列に保存するための単純なラッパーを作成できます。
namespace bar = boost::archive;
namespace bio = boost::iostreams;
template <class T> inline std::string saveString(const T & o) {
std::ostringstream oss;
bar::binary_oarchive oa(oss);
oa << o;
return oss.str();
}
template <class T> inline void saveFile(const T & o, const char* fname) {
std::ofstream ofs(fname, std::ios::out|std::ios::binary|std::ios::trunc);
bar::binary_oarchive oa(ofs);
oa << o;
}
template <class T> inline void loadFile(T & o, const char* fname) {
std::ifstream ifs(fname, std::ios::in|std::ios::binary);
assert(ifs.good()); // XXX catch if file not found
bar::binary_iarchive ia(ifs);
ia >> o;
}
問題は、シリアル化されたデータも圧縮する必要があることを発見したので、boost::iostreamsのフィルターを使用してそれを行うことを検討しています。私はファイルでそれをうまく行う方法を考え出しました:
template <class T> inline void saveGZFile(const T & o, const char* fname) {
std::ofstream ofs(fname, std::ios::out|std::ios::binary|std::ios::trunc);
bio::filtering_streambuf<bio::output> out;
out.push(boost::iostreams::gzip_compressor());
out.push(ofs);
bar::binary_oarchive oa(out);
oa << o;
}
template <class T> inline void loadGZFile(T & o, const char* fname) {
std::ifstream ifs(fname, std::ios::in|std::ios::binary);
assert(ifs.good()); // XXX catch if file not found
bio::filtering_streambuf<bio::input> in;
in.push(bio::gzip_decompressor());
in.push(ifs);
bar::binary_iarchive ia(in);
ia >> o;
}
しかし、圧縮された文字列に正しく保存する方法を理解することはできません。問題は、フィルターのチェーンをフラッシュしていないことですが、ポップと同期を試しましたが、何も機能しないようです。これが私の壊れたコードです:
template <class T> inline std::string saveGZString(const T & o) {
std::ostringstream oss;
bio::filtering_streambuf<bio::output> out;
out.push(bio::gzip_compressor());
out.push(oss);
bar::binary_oarchive oa(out);
oa << o;
// XXX out.pop() twice? out.strict_sync()?? oss.flush()??
return oss.str();
}
その結果、一部のデータがストリームバッファのどこかにスタックし、43K程度であることがわかっている場合、圧縮データの完全なブロック(16Kまたは32K)が常にいくつかあります。私のsaveGZFileメソッド。どうやらofstreamを接続すると、適切に閉じてフラッシュしますが、ostringstreamを接続してもそうではありません。
何か助けはありますか?(これは私の最初のstackoverflowの質問です—助けてください、みんな、あなたは私の唯一の希望です!)