3

我想使用 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

2 回答 2

5

您需要为指向的对象分配内存pItem

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

错误是因为虽然你有一个指针,但指针指向的内存位置没有对象——指针的值是垃圾(未初始化的指针)。

delete当您不再需要向量中的指针指向的对象时,不要忘记调用以防止内存泄漏。更好的是,使用智能指针(例如boost::shared_ptr<>)来确保内存在不再可访问时被释放。

于 2012-06-07T16:34:12.443 回答
3

2年后,但值得一提。

有一个更好的解决方案来序列化指向对象或任何其他 STL 容器(列表、集合等)的指针向量。为了序列化一个向量,添加:

#include <boost/serialization/vector.hpp>

然后你需要实现 serialize() 方法并将你的类与archieve 成为朋友。这个例子中解释了一切(仔细阅读所有评论,它们非常重要):

#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

于 2014-04-21T14:45:12.037 回答