2012-06-07 2 views
3

Я хочу сериализации/десериализации с помощью BOOST значения (а не указатели) объектов в следующем векторе:Векторный указателей. BOOST сериализации

std :: vector <A*> m_vector; 

Для сериализации Я использую следующий код:

int nItems = m_vector.size(); 
ar & nItems; 
std::for_each(m_vector.begin(), m_vector.end(), [&ar](A* pItem) { 
    ar & *pItem; 
}); 

И к десериализации:

int nItems; 
ar & nItems; 
for (int i = 0; i < nItems; ++i) { 
    A* pItem; 
    ar & *pItem; ///////////// Run-Time Check Failure #3 
    m_vector.push_back(pItem); 
} 

Но когда я запускаю программу, я получаю следующее сообщение об ошибке:

Run-Time Check Failure # 3 - The variable 'pItem' is Being Used without Being initialized. 

Что я делаю неправильно?

спасибо.

ответ

4

Вам нужно будет выделить память для объекта, на который указывает pItem:

A* pItem = new A; 
ar & *pItem; 
m_vector.push_back(pItem); 

Обнаружена ошибка, потому что, хотя вы были указатель, не было ни одного объекта в ячейку памяти, где указатель указывал на - значение указателя было мусором (неинициализированный указатель).

Не забудьте позвонить delete, когда вам больше не нужен объект, на который указывает указатель в векторе, на предотвращенную утечку памяти. Еще лучше использовать интеллектуальный указатель (например, boost::shared_ptr<>), чтобы обеспечить освобождение памяти, когда она больше не доступна.

+0

Спасибо за вашу помощь. –

+1

@JoanCarles - пожалуйста, примите ответ, если он поможет вам решить проблему. – Attila

1

2 года спустя, но стоит упомянуть.

Было лучшее решение для сериализации вектора указателей на объекты или любого другого контейнера STL (список, набор и т. Д.). Для того, чтобы сериализовать вектор, добавьте:

#include <boost/serialization/vector.hpp> 

, а затем вам нужно реализовать Serialize() метод и друг ваш класс с АРХИВ. Все объясняется в данном примере (читать все комментарии тщательно, они очень важны):

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

#include <boost/archive/text_oarchive.hpp> 
#include <boost/archive/text_iarchive.hpp> 
#include <boost/serialization/vector.hpp> 


class Abc{ 
    // In order to make Abc serializable 
    // you need to friend this lass with serialization::access 
    friend class boost::serialization::access; 

    // and then add this method 
    template<class Archive> 
    void serialize(Archive & ar, const unsigned int version) 
    { 
     // choose what class fields do you want to serialize 
     ar & a; 
     ar & b; 
     ar & c; 
    } 
public: 
    int a; 
    int b; 
    int c; 

    // don't forget about default constructor! It's necessary for serialization! 
    Abc(){}; 
    Abc(int a, int b, int c): a(a), b(b), c(c){}; 
}; 

class GpsPosition 
{ 
private: 
    // as mentioned above... 
    friend class boost::serialization::access; 
    template<class Archive> 
    void serialize(Archive & ar, const unsigned int version) 
    { 
     ar & degrees; 
     ar & minutes; 
     ar & seconds; 
     ar & wektorIntow; 
    } 
    int degrees; 
    int minutes; 
    float seconds; 
public: 
    std::vector<Abc*> abcVector; 
    GpsPosition(){}; 
    GpsPosition(int d, int m, float s): degrees(d), minutes(m), seconds(s) 
    { 
     // adding some objects to abcVector 
     abcVector.push_back(new Abc(1, 2, 3)); 
     abcVector.push_back(new Abc(3, 2, 3)); 
     abcVector.push_back(new Abc(2, 2, 3)); 
     abcVector.push_back(new Abc(1, 2, 3)); 
    } 
    int getDegrees(){ return this->degrees; } 
    int getMinutes(){ return this->minutes; } 
    float getSeconds(){ return this->seconds; } 
}; 

int main(){ 

    // And now how to use it 

    // Saving to file: 
    std::ofstream fileHandler("filename"); 
    const GpsPosition position1(35, 59, 24.567f); 
    { 
     boost::archive::text_oarchive boostOutputArchieve(fileHandler); 
     boostOutputArchieve << position1; 
    } 

    // Reading from file: 
    GpsPosition newPosition; 
    { 
     std::ifstream fileHandler; 
     try{ 
      fileHandler.open("filenacme"); 
      boost::archive::text_iarchive boostInputArchieve(fileHandler); 
      // read class state from archive 
      boostInputArchieve >> newPosition; 
      // archive and stream closed when destructors are called 
      fileHandler.close(); 
      } 
     catch (std::ifstream::failure e) { 
      std::cerr << "Exception opening/reading/closing file"; 
     } 
     catch(boost::archive::archive_exception e){ 
      std::cerr << "Exception opening/reading/closing file"; 
     } 
    } 

    // print to the console 
    std::cout << newPosition.getMinutes() << std::endl; 
    std::cout << newPosition.abcVector[0]->a; 
    std::cin.get(); 

    return 0; 
} 

Для получения дополнительной информации, проверить этот учебник: http://www.boost.org/doc/libs/1_55_0/libs/serialization/doc/index.html

+0

Я полагаю, что «wektorIntow» и «abcVector» должны иметь одно и то же имя? – Maverobot

Смежные вопросы