天天看点

使用Boost Serialization序列化保存各类对象

一、前言

1、在编程中有时会有这样的需求:
  • 保存内存中的对象到磁盘上,下次运行时直接读取该对象,不用再重新赋值,对于那些对象特别大,赋值时间长的对象来说能大大提高速度。比如我现在有一个存储着100万条数据的Map对象,如果把Map中的每条数据存入磁盘,然后再进行读取重新insert的话,这样耗时肯定很久;如果把Map对象直接保存到磁盘中,然后读取文件,读取出来不用重新insert,直接用,这样将会更方便
  • 通过网络传输对象
2、序列化

能实现上面操作的方法叫做序列化:

序列化在计算机科学中通常有以下定义:

对同步控制而言,表示强制在同一时间内进行单一存取。

在数据储存与传送的部分是指将一个对象存储至一个储存媒介,例如档案或是记亿体缓冲等,或者透过网络传送资料时进行编码的过程,可以是字节或是XML等格式。而字节的或XML编码格式可以还原完全相等的对象。这程序被应用在不同应用程序之间传送对象,以及服务器将对象储存到档案或数据库。相反的过程又称为反序列化。

3、Boost Serialization

Boost 提供的序列化操作起来非常简单,先看一个非常简单的例子:

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

struct employee
{
    int         id;
    int         age;
    employee()
    :id(),age() {}
    employee(int id_,int age_) :id(id_),age(age_) {}

    template<class Archive>
    void serialize(Archive & ar, const unsigned int version)
    {
        ar & id;
        ar & age;
    }
};
void save(const employee& es)
{
    std::ofstream ofs("data");
    boost::archive::text_oarchive oa(ofs);
    oa << es;
}

void load(employee& es)
{
    std::ifstream ifs("data");
    boost::archive::text_iarchive ia(ifs);
    ia >> es;
}

int main()
{
    employee e1(,);
    save(e1);
    employee e2;
    load(e2);
    return ;
}
           

这样e2就和e1相同了。

需要注意的是,自定义的结构或类中必须实现serialize方法,然后把需要保存的成员写在函数里。

除了可以保存自定义类型外,还可以保存STL中的各类容器,但是需要注意一点,因为需要实现serialize方法,所以引入的头文件不是STL的头文件,而是Booat实现的头文件。例如想保存vector对象,那么需要引入

#include < boost/serialization/vector.hpp >,其他类型同理。

其他

1、如果不想改变类中的函数,新增serialize函数,还可以采用这种

namespace boost {
namespace serialization {

template<class Archive>
    void serialize(Archive & ar, employee& g, const unsigned int version)
    {
        ar & g.id;
        ar & g.age;
    }
} // namespace serialization
} 
           

2、如果自定义类型中含有位域的会,直接采用以上方法会出错,正确的方法如下

struct Test
{
    char bits1 : ;
    char bits2 : ;
    char bits3 : ;

    template<class Archive>
    void serialize(Archive & ar, const unsigned int version)
    {
        char tmp1 = bits1;
        char tmp2 = bits2;
        char tmp3 = bits3;
        ar & BOOST_SERIALIZATION_NVP(tmp1);
        ar & BOOST_SERIALIZATION_NVP(tmp2);
        ar & BOOST_SERIALIZATION_NVP(tmp3);
        bits1 = tmp1;
        bits2 = tmp2;
        bits3 = tmp3;
    }
}