1. 暂时使用boost 序列化, 目前我的测试基本都ok 只是对于c++11 shared ptr 没有测试成功,只能手工写下shared ptr 部分的序列化,也就是目前我对指针都不直接序列化,自己管理,例如下面样子

    Load_(modelFile); //model直接序列化

    string normalizerName = read_file(OBJ_NAME_PATH(_normalizer));

    if (!normalizerName.empty())

    { //由于没有利用shared ptr直接序列化,不知道具体信息,所以我save的时候写了normalzier类型名字到文本,load时候通过这个确定类型

    _normalizer = NormalizerFactory::CreateNormalizer(normalizerName, OBJ_PATH(_normalizer));

    }

    string calibratorName = read_file(OBJ_NAME_PATH(_calibrator));

    if (!calibratorName.empty())

    {

    _calibrator = CalibratorFactory::CreateCalibrator(calibratorName, OBJ_PATH(_calibrator));

    }

    static NormalizerPtr CreateNormalizer(string name)

    {

    boost::to_lower(name);

    if (name == "minmax" || name == "minmaxnormalizer")

    {

    return make_shared<MinMaxNormalizer>();

    }

    if (name == "gaussian" || name == "gaussiannormalizer")

    {

    return make_shared<GaussianNormalizer>();

    }

    if (name == "bin" || name == "binnormalizer")

    {

    return make_shared<BinNormalizer>();

    }

    LOG(WARNING) << name << " is not supported now, do not use normalzier, return nullptr";

    return nullptr;

    }

     
     

    static NormalizerPtr CreateNormalizer(string name, string path)

    {

    NormalizerPtr normalizer = CreateNormalizer(name);

    if (normalizer != nullptr)

    {

    normalizer->Load(path); //normalzier直接序列化

    }

    return normalizer;

    }

     
     

    @TODO 确认下是否没有办法直接序列化shared ptr,

    另外可以尝试下开源的专门序列化库creal,creal仿照boost 序列化 同时boost序列化只支持binary,文本,xml三种序列化,文本序列化可读性不强,binary速度最快,xml可读性最高速度慢一些。我一般只用binary和xml格式。而creal 支持json格式的输出,号称支持shared ptr

     
     

    同一个模型boost序列化速度

  

Binary

Text

Save

1.8

2.29

Load

1.9

2.67

 
 

 
 

  1. 如果需要xml输出,boost的序列化写法和只需要binary输出不一样,建议采用支持xml输出的写法这样互相都兼容。

     
     

    friend class boost::serialization::access;

    template<class Archive>

    void serialize(Archive &ar, const unsigned int version)

    {

    /*        ar & boost::serialization::base_object<Predictor>(*this);

    ar & _weights;

    ar & _bias;*/ //这种写法只支持binary

    ar & BOOST_SERIALIZATION_BASE_OBJECT_NVP(Predictor);

    ar & BOOST_SERIALIZATION_NVP(_weights); //这样宏比较方便 如果需要改名字比如_weights->weights可以使用原函数

    ar & BOOST_SERIALIZATION_NVP(_bias);

    }

     
     

     
     

  2. 采用python脚本自动生成序列化部分的代码。因为和c#不一样 c#是默认都可以序列化,如果不需要序列化,你可以类似#define指定,而boost默认都不序列化,需要序列化的地方需要显示都写上

    Predictors]$ get-lines.py LinearPredictor.h 98 99 | gen-boost-seralize-xml.py

     
     

    friend class boost::serialization::access;

    template<class Archive>

    void serialize(Archive &ar, const unsigned int version)

    {

    ar & BOOST_SERIALIZATION_NVP(_weights);

    ar & BOOST_SERIALIZATION_NVP(_bias);

    }

     
     

4. 对于Predictor 默认是Save二进制,可选的SaveXml方式这个自动支持,可选的SaveText这个是特定的Precitor子类型如果有需要手动写的文本输出格式。

xml输出类似这样

 
 

转换为json

xml2json.py model.xml > model.json

more model.json

采用json pretty print来查看json文件

jpp.py model.json | more

 
 

Xml2tojson.py 利用xmltodict 进行向json的转换

 
 

import sys,os

import xmltodict, json

doc = xmltodict.parse(open(sys.argv[1]), process_namespaces=True)

print json.dumps(doc)

 
 

Jpp.py

import sys,os

import json

s = open(sys.argv[1]).readline().decode('gbk')

print json.dumps(json.loads(s),sort_keys=True, indent=4, ensure_ascii=False).encode('gbk')

 
 

  1. 如何更方便的查看输出的模型?

    小的模型输出直接看xml文本就好,如果数据比较多处理xml不是很方便,json好一些 用python,

    但是如果转换为json的map也不是很方便因为你要按照key去访问string类型是没有自动提示的

     
     

    In [6]: import json

     
     

    In [7]: m = json.loads(open('./model.json').readline())

     
     

    In [8]: m.keys()

    Out[8]: [u'boost_serialization']

     
     

    In [9]: m['boost_serialization'].keys()

    Out[9]: [u'@version', u'@signature', u'data']

     
     

    In [18]: m['boost_serialization']['data']['_trees']['item'][0].keys()

    Out[18]:

    [u'_gainPValue',

    u'@tracking_level',

    u'@class_id',

    u'_lteChild',

    u'_gtChild',

    u'_maxOutput',

    u'_leafValue',

    u'NumLeaves',

    u'_splitGain',

    u'_splitFeature',

    u'_previousLeafValue',

    u'_threshold',

    u'@version',

    u'_weight']

     
     

    In [19]: m['boost_serialization']['data']['_trees']['item'][0]['_splitGain']['item'][10]

    Out[19]: u'3.89894126598927926e+00'

     
     

    由于python提示的时候_开头的作为private默认是不提示的,因此做了修改

    #include "conf_util.h"

    #include <boost/serialization/nvp.hpp>

    #define GEZI_SERIALIZATION_NVP(name)\

    boost::serialization::make_nvp(gezi::conf_trim(#name).c_str(), name)

     
     

    这样展示的就是gainPvalue这样没有_开头了

     
     

    利用python的自省功能可以把json解析得到的dict数据,string作为key的转为一个python object方便访问如下

    def h2o(x):

    if isinstance(x, dict):

    return type('jo', (), {k: h2o(v) for k, v in x.iteritems()})

    elif isinstance(x, list):

    l = [h2o(item) for item in x]

    return l

    else:

    return x

     
     

    def h2o2(x):

    if isinstance(x, dict):

    return type('jo', (), {k: h2o2(v) for k, v in x.iteritems()})

    elif isinstance(x, list):

    return type('jo', (), {"i" + str(idx): h2o2(val) for idx, val in enumerate(x)})

    return l

    else:

    return x

     
     

    def xmlfile2obj(path):

    import xmltodict

    doc = xmltodict.parse(open(path), process_namespaces=True)

    return h2o(doc)

     
     

    def xmlfile2obj2(path):

    import xmltodict

    doc = xmltodict.parse(open(path), process_namespaces=True)

    return h2o2(doc)

     
     

    这样对于序列化之后的xml文件可以直接使用 m = xmlfile2obj('*.xml') 或者 m = xml2obj2('*.xml')

    建议是用第一种,是标准转换,提供第二个接口主要是python的自动提示对于list的item就没有了,只能dir()查看。。

    第二种将[3]这样转为了.i3也就是去掉了所有list都用dict表示。

     
     

    m = xmlfile2obj('./model.xml')

    In [14]: m.boost_serialization.data.trees.item[0].splitGain.item[13]

    Out[14]: u'3.26213753939964946e+00'

     
     

    m = xmlfile2obj2('./model.xml')

    In [16]: m.boost_serialization.data.trees.item.i0.splitGain.item.i13

    Out[16]: u'3.26213753939964946e+00'

     
     

     
     

     
     

     
     

     
     

 
 

c++序列化方法的更多相关文章

  1. Django的DRF序列化方法

    安装rest_framework -- pip install djangorestframework -- 注册rest_framework序列化 -- Python--json -- 第一版 用v ...

  2. jquery字符串序列化方法总结

    在jquery中字符串序列化方法包括有param() .serialize() .serializeArray(),在这里对其常用做法进行总结. $.param()方法这是serialize()方法的 ...

  3. (转)C# 的三种序列化方法

    序列化是将一个对象转换成字节流以达到将其长期保存在内存.数据库或文件中的处理过程.它的主要目的是保存对象的状态以便以后需要的时候使用.与其相反的过程叫做反序列化. 序列化一个对象 为了序列化一个对象, ...

  4. C# 的三种序列化方法

    序列化是将一个对象转换成字节流以达到将其长期保存在内存.数据库或文件中的处理过程.它的主要目的是保存对象的状态以便以后需要的时候使用.与其相反的过程叫做反序列化. 序列化一个对象 为了序列化一个对象, ...

  5. django drf 10大请求序列化方法

    ## 整体单改 路由层.模型层.序列化层不需要做修改,只需要处理视图层:views.py ```python"""1) 单整体改,说明前台要提供修改的数据,那么数据就需要 ...

  6. 自已写的Json序列化方法,可以序列话对象的只读属性

    /* * by zhangguozhan 2015/1/5 * P2B.Common.CJson.ConvertJson.ObjectToJson<SenderDomainModel>方法 ...

  7. 分享一个 jquery serializeArray()序列化方法

    http://www.365mini.com/page/jquery-serializearray.htm http://www.365mini.com/diy.php?f=jquery-serial ...

  8. Redis 数据序列化方法 serialize, msgpack, json, hprose 比较

    最近弄 Redis ,涉及数据序列化存储的问题,对比了:JSON, Serialize, Msgpack, Hprose 四种方式 1. 对序列化后的字符串长度对比: 测试代码: $arr = [0, ...

  9. 配置spring cache RedisCacheManager的序列化方法

    通过查看autoconfigure源码 org.springframework.boot.autoconfigure.cache.RedisCacheConfiguration; 部分源码如下: pr ...

随机推荐

  1. C#高级编程笔记 Day 3, 2016年9月 8日 抽象类

    1.虚方法:把一个基类函数声明为 virtual,就可以在任何派生类中重写该函数. 2.在Java 中所有函数都是虚拟的,但是在C# 中,C# 要求在派生类的函数重写另一个函数时,要使用 overri ...

  2. 跟着百度学PHP[4]OOP面对对象编程-8-继承

    如下图所示.人就是父类!而NBA球员以及女主播就是子类 要继承一个类,那么在类名的后面加上extends 要继承的类名 具体格式:class Student extends human{}     # ...

  3. poj 1797(并查集)

    http://poj.org/problem?id=1797 题意:就是从第一个城市运货到第n个城市,最多可以一次运多少货. 输入的意思分别为从哪个城市到哪个城市,以及这条路最多可以运多少货物. 思路 ...

  4. [Linux]centOS7下RPM安装Perl

    1.下载rpm依赖包,依照顺序安装. perl-parent-0.225-244.el7.noarch   perl-HTTP-Tiny-0.033-3.el7.noarch   perl-podla ...

  5. Linux下安装Django

    Django是基于Python开发的免费的开源网站框架,也是python web开发中重量级的web框架,可以用于快速搭建高性能并且优雅的网站! 下面以Fedora为例安装Django,最新Fedor ...

  6. K3问题 无法创建中间层 组件<KdSvrMgr>无法正常工作

    K3遇到如下问题 一直无法解决,这个是本地计算机的问题,跟服务器没关系,采用笨方法,重装K3(重装到本磁盘.其他磁盘),重装系统,虽然笨,但最后都解决掉了

  7. Effective C++ -----条款32:确定你的public继承塑模出is-a关系

    “public继承”意味is-a.适用于base classes身上的每一件事情一定也适用于derived classes身上,因为每一个derive class对象也都是一个base class对象 ...

  8. event.srcElement 用法笔记e.target

    event.srcElement 可以捕获当前事件作用的对象,如event.srcElement.tagName可以捕获活动标记名称. 注意获取的标记都以大写表示,如"TD",&q ...

  9. CCF I'm Stuck!

    问题描述 试题编号: 201312-5 试题名称: I'm stuck! 时间限制: 1.0s 内存限制: 256.0MB 问题描述: 问题描述 给定一个R行C列的地图,地图的每一个方格可能是'#', ...

  10. GCD的使用

    什么是 GCD Grand Central Dispatch (GCD) 是 Apple 开发的一个多核编程的解决方法.该方法在 Mac OS X 10.6 雪豹中首次推出,并随后被引入到了 iOS4 ...