bitcoin数据的序列化

在bitcoin的p2p网络以及rpc调用中,需要将数据进行序列化后后再发送。本文主要介绍一下bitcoin中的序列化部分函数功能。

下面主要从rpc调用中说明。

首先,我们知道rpc中的数据类型是json,可以理解成一个键值对的形式。那么对于json格式的数据,目标是将json中的键和值都转化成字符串。因为rpc中的json的键一定是string的格式,所以只需要将值序列化成字符串的格式就可以。但是问题在于json的值的类型是各种各样的,可能是数组,可能是对象,可能是结构体,其中自定义的类的对象无法确定,因此需要一个合理的序列化机制。

如何建立一个合理的序列化机制?

先看看序列化的数据的构成

可以看到,无论是c++中的基类还是用户自定义的类,都可以转化成基类的序列化,因为,用户自定义的类都是基于基类创建的(可能是继承,也可能是组合,或者同时是继承和组合),因此首先要解决基类的序列化。我们可以看到在bitcoin的serialize.h文件中定义了很多基于各个基类的序列化函数

bitcoin数据的序列化_第1张图片

ok,现在基类的序列化搞定了,那么用户自定义类呢?很简单,对于一个类,我们只需要序列化它的数据成员就可以了,而数据成员的序列化即可以直接调用这些基类函数(这里就体现了函数多态的优越性,我们只需要根据参数的类型定义一个同名称的函数即可)。

ok,但是现在还有一个问题,就是如果一个用户自定义类里面有一个自定义的类的对象成员怎么办?解决方案是,对于每一个自定义的类,我们都定义一个序列化自身的函数,这样当需要序列化一个自定义的对象的时候,我们只需要分别调用它的成员数据的序列化函数,然后将结果合并在一起即可。(这里类似一个递归,即序列化一个对象,需要序列化对象中的对象,而递归的出口是,需要序列化的对象是一个基类的对象)

但是,其实上面的方案仍旧有一个问题,那就是如果这个对象中存在变长的数据结构,那如何正确的反序列化呢?比如map和vector等

解决方案是,对于这种变长的数据类型,先填入该数据的长度(指的是数组或者map的size,即元素的数量)然后再分别序列化每一个元素。对于每一个元素而言,如果该元素也是一个变长数据结构,也采用先填长度,再填元素的方法即可(注意这里也是一个递归,计算机真的是递归的世界呀!)

-----------------------------------------------------------------------------------------------------------------------------

转载请注明出处。

 

 

你可能感兴趣的:(bitcoin,bitcoin,serialize)