Boost.Serialization和Boost.Python双向泡菜

时间:2011-09-02 22:43:46

标签: c++ python boost pickle boost-serialization

我有一个使用Boost.Serialization的C ++库。我正在使用Boost.Python为这个库创建Python绑定。很明显如何为Boost.Python创建一个使用Boost.Serialization的pickle套件(使用Boost.Serialization保存为字符串,并将该字符串返回给Python)。

我想要的是反过来:给定一个boost::python::object,我希望有一个serialize(...)函数来调用Python的pickle.dumps()函数并序列化生成的字符串。 (想象一下std::vector<boost::python::object>。当我序列化这个向量时,Boost.Serialization会调用辅助serialize()函数。)这可能吗?更好的是,是否可以使用cPickle并绕过将控件提供给Python解释器?

2 个答案:

答案 0 :(得分:0)

这是我用来pickle / unpickle boost :: mersenne_twister实例的代码

typedef boost::mt19937 rng_t;

struct mt_pickle_suite : bp::pickle_suite {

  static bp::object getstate (const rng_t& rng) {
    std::ostringstream os;
    boost::archive::binary_oarchive oa(os);
    oa << rng;
    return bp::str (os.str());
  }

static void
  setstate(rng_t& rng, bp::object entries) {
    bp::str s = bp::extract<bp::str> (entries)();
    std::string st = bp::extract<std::string> (s)();
    std::istringstream is (st);

    boost::archive::binary_iarchive ia (is);
    ia >> rng;
  }
};

答案 1 :(得分:0)

如果您的对象是本机python对象,则可以使用pickle.dumps()完成操作。

另一方面,如果您有std :: vector,则您正在混合使用c ++和python。为此,您将需要注册std :: vector,如:

using PyVec = std::vector<boost::python::object>;
boost::python::_class<PyVec, boost::noncopyable>
    ("PyVec", "My vector of PyObjects", boost::python::init<>() )
    .enable_pickling()
    .def_pickle( py_vec_pickle_suit() );

然后,您当然需要定义一个泡菜服。但这太麻烦了。

TL; DR:改为使用boost :: python :: list并在其上调用转储。