Boost logo

Boost :

Subject: [boost] [serialization]Can I pass the grandparent class to BOOST_SERIALIZATION_BASE_OBJECT_NVP?
From: Takatoshi Kondo (kondo_at_[hidden])
Date: 2011-04-03 06:59:01


Hi,
I'd like to check that my approach is correct or not.

Condition:
There are three classes A, B and C.
The class A is the base class of B.
The class B is the base class of C.

Requirements:
 1.The class A and B shouldn't depend on the serialization library.
 2.The class C should be serialized via the base class A (Polymorphic).

My approach:
Applying non intrusive version serialize function to the class A and B.
In the class C, using the macro BOOST_SERIALIZATION_BASE_OBJECT_NVP
with the argument A (not B).

I skip the class B in the class hierarchy on purpose.
If I pass it B instead of A, the following exception would be occurred.
"unregistered void cast struct C<-struct A"

I believe that my approach is correct. (using A)

But I suspect that it might work correctly by accident.

#include <boost/serialization/serialization.hpp>
#include <boost/archive/xml_oarchive.hpp>
#include <boost/archive/xml_iarchive.hpp>
#include <boost/serialization/nvp.hpp>
#include <boost/serialization/export.hpp>

#include <fstream>

struct A {
    virtual ~A() {}
};
// non intrusive serialize
namespace boost { namespace serialization {
template<class Archive>
void serialize(Archive& /*ar*/, A&, unsigned int const /*version*/) {}
}}

struct B : public A {};
// non intrusive serialize
namespace boost { namespace serialization {
template<class Archive>
void serialize(Archive& /*ar*/, B&, unsigned int const /*version*/) {}
}}

struct C : public B {
    friend class boost::serialization::access;
    template<class Archive>
    void serialize(Archive& ar, unsigned int const /*version*/) {
        ar & BOOST_SERIALIZATION_BASE_OBJECT_NVP(A); // My approach
// ar & BOOST_SERIALIZATION_BASE_OBJECT_NVP(B);
    }
};
BOOST_CLASS_EXPORT(C)

int main()
{
    {
        std::ofstream ofs("test.xml");
        C c ;
        A* a(&c);
        boost::archive::xml_oarchive oa(ofs);
        oa << boost::serialization::make_nvp("a", a);
    }
    {
        std::ifstream ifs("test.xml");
        boost::archive::xml_iarchive ia(ifs);
        A* a;
        ia >> boost::serialization::make_nvp("a", a);
        assert(dynamic_cast<C*>(a));
        delete a;
    }
}

Regards,
Takatoshi Kondo


Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk