boost serialization and register_type

2020-08-15 03:33发布

问题:

I have a problem in an application i'm doing. I need to serialize some packets using boost serialization. According to the documentation, one can use BOOST_CLASS_EXPORT_KEY and BOOST_CLASS_EXPORT_IMPLEMENT respectively into .hpp and .cpp files to be able to use polymorphic base pointer to serialize derived class.

So here is what I have:

.hpp: containaing my class declaration and finaly the BOOST_CLASS_EXPORT_KEY(mynamespace::mypacket)

.cpp: containing my class definition and the BOOST_CLASS_EXPORT_IMPLEMENT(mynamespace::mypacket)

Everything runs fine till this point but when needing to serialize I get a bad_alloc error.

I worked arround this problem by explicitly calling the method register_type<mypacket>() on the archive i need to use.

But here is my question : Is the EXPORT* of boost meant to avoid calls to register_type method or am I doing something wrong? I kind of feel like doing twice the same work in my code, but more than that I don't see any advantage of using export key + implement if we still have to use register_type on archive after!

I read some other posts here and elsewhere, it seems I'm not the only one to experiment the problem, but I have not found any answer yet.

回答1:

i figured out how to avoid calling register_type on archive. For those who might be interested, it is needed to do template serialization specialization as well as exporting key + implement.

So here is what your .hpp should look like :

  • class declaration (mynamespace::myclass)
  • class export : BOOST_CLASS_EXPORT_KEY(mynamespace::myclass)

And in the cpp:

  • class definiton
  • class export : BOOST_CLASS_EXPORT_IMPLEMENT(mynamespace::myclass)
  • AND : serialize() member specialization on the archive you need to use, for each class :

template void mynamespace::mypacket::serialize(boost::archive::text_iarchive& arch, const unsigned int version);

template void mynamespace::mypacket::serialize(boost::archive::text_oarchive& arch, const unsigned int version);

Where boost::archive::text_(i/o)archive should be replaced with whatever kind of boost archive you are using.

In hope it will help someone someday (this is clearly written in the boost documentation, but i must have missed it till today...)