2010-12-13 15 views
9

que he estado leyendo, referencias cruzadas, y en última instancia no encontrar un ejemplo coherente y respuesta. Lo que intento hacer es bastante simple, pero claramente me falta algo. en Inglés, tengo una estructura de clases con dos bases abstractas (BB pura deriva de AA puro), que me las arreglo como:impulso serialización excepción: clase no registrada, la serialización problema de base polimórfica

std::vector<AA*> 

me gustaría serializar otro objeto que contiene este vector. todo excepto este vector serializa bien, pero una vez que llega al vector, se lanza:

terminate called after throwing an instance of 'boost::archive::archive_exception' 
    what(): unregistered class - derived class not registered or exported 

He intentado un par de cosas, incluyendo el registro de forma explícita los tipos de padres antes de la serialización, declarando expresamente la base abstracta clases como tales con 'BOOST_SERIALIZATION_ASSUME_ABSTRACT', etc. Sin embargo, me quedo con la excepción en tiempo de ejecución.

me gustaría conseguir este ejemplo (y solución) en el registro para que otros usuarios pueden utilizar esta excelente, aunque un poco opaco, biblioteca. una vez que este ejemplo es cuadrada, voy a presentar a los responsables del impulso de serialización para incluir en cualquiera de las preguntas más frecuentes o documentación que les parezca.

código de ejemplo para replicar el problema a continuación:

/* 
    g++ -Iinclude/ -Llib -lboost_serialization ~/Desktop/ser_ex.cpp -o stest 
*/ 
#include <boost/serialization/serialization.hpp> 
#include <boost/serialization/nvp.hpp> 
#include <boost/archive/xml_oarchive.hpp> 
#include <boost/serialization/vector.hpp> 

#include <iostream> 
#include <fstream> 
#include <string> 
#include <vector> 

namespace bser = boost::serialization; 
class AA 
{ 
public: 
    virtual void foo() = 0; 
    std::string name; 

    template<class Archive> 
    void serialize(Archive & ar, unsigned int file_version) 
    { 
     ar & bser::make_nvp("Name", name); 
    } 
}; 
BOOST_SERIALIZATION_ASSUME_ABSTRACT(AA); 

class BB : public AA 
{ 
public: 
    virtual void foo() = 0; 
    virtual void bar() = 0; 
    int thing; 

    template<class Archive> 
    void serialize(Archive & ar, unsigned int file_version) 
    { 
     ar.template register_type<AA>(); 
     ar & bser::base_object<AA>(*this); 
     ar & bser::make_nvp("Thing", thing); 
    } 
}; 
BOOST_SERIALIZATION_ASSUME_ABSTRACT(BB); 

class CC : public BB 
{ 
public: 
    virtual void foo() {} 
    virtual void bar() {} 
    int otherThing; 

    template<class Archive> 
    void serialize(Archive & ar, unsigned int file_version) 
    { 
     ar.template register_type<BB>(); 
     ar & bser::base_object<BB>(*this); 
     ar & bser::make_nvp("OtherThing", otherThing); 
    } 
}; 

int main (int argc, char const *argv[]) 
{ 
    const std::string filename("my.serialized"); 
    const std::string key("AAVector"); 

    std::vector< AA* > vv; 
    vv.push_back(new CC); 

    std::ofstream outfilestream(filename.c_str(), std::ios::binary); 
    boost::archive::xml_oarchive out_archive(outfilestream); 
    out_archive << boost::serialization::make_nvp(key.c_str(), vv); 
    outfilestream.close(); 
} 

Respuesta

6

Tengo esto para trabajar con pequeñas modificaciones:

  • Reemplazar ar & bser::base_object<AA>(*this); en BB::serialize con:

    ar & BOOST_SERIALIZATION_BASE_OBJECT_NVP(AA); 
    
  • Reemplazar ar & bser::base_object<BB>(*this); en CC::serialize con:

    ar & BOOST_SERIALIZATION_BASE_OBJECT_NVP(BB); 
    
  • Añadir un BOOST_CLASS_EXPORT(CC) después CC definición. Ver this documentation section una explicación.

Cuestiones relacionadas