【问题标题】:Serialize a class in C++在 C++ 中序列化一个类
【发布时间】:2012-10-04 20:10:01
【问题描述】:

有没有办法在 C++ 中序列化一个类?我指的不是类的实例,而是类本身。反序列化时,我不知道要实例化哪个类来调用反序列化。我希望能够以某种方式确定所表示的类,实例化它的一个空实例,然后调用反序列化它。

编辑澄清:

我正在创建一个键值结构,其中每个键都有一个强类型值。 (一些键必须存储字符串,其他键必须存储整数,还有一些键可以存储任意值)。我设计了一个系统,由编译器通过模板强制执行。

Key 类有两个模板参数:

  • UniqueClass - 每个概念应该有一个唯一的类(通常在定义概念的预处理器函数中定义)
  • ValueType - 这是该概念的值必须属于的类

Value 类是一个模板类,只有 ValueType 有一个抽象超类,因此我可以在其中包装任何类(类似于 boost::any)。

然后在我的键值结构中,我存储和检索使用 ConceptType 和 ValueType 模板化的函数:

template<UniqueClass, ValueType>
void store( Concept<UniqueClass, ValueType> concept, ValueType value );

因为我使用相同的模板来描述 Concept 的值类型和传入的值,如果它们不匹配,编译器会报错。

我现在希望能够序列化键值存储。因此,我需要以某种方式序列化模板化的 Concept 类,然后在反序列化期间实例化正确的任意类。

我有它,以便我可以调用 serialize 并要求所有适当的对象序列化自己,我只是不知道在反序列化期间要实例化哪个类来要求反序列化自身。

【问题讨论】:

  • 请解释一下“序列化类”是什么意思。序列化什么,定义(方法/字段)?静态成员?
  • 显示一些你试图开始工作的非工作代码。
  • 您的问题并没有立即明确,但您似乎要求的是两种不同的东西。 1)如何确定要反序列化的类类型(这将需要一些序列化的元数据并且可以使用某种类型的工厂模式)和 2)如何实际序列化内容(可以通过多种方式完成)。这里有一些示例可以帮助您入门:boost.org/doc/libs/1_51_0/libs/serialization/doc/index.html
  • 您的序列化字段之一将需要一些元数据信息,以便您可以确定要实例化的正确类型。我会想出一个示例答案。
  • 你的概念是一个关系unique class &lt;-&gt; value type。一个unique class 可以关联多个value type 吗?

标签: c++ templates serialization deserialization


【解决方案1】:

由于问题编辑已更新答案:

我的理解是,在您手动添加或通过反序列化添加之前,您在容器中有 0 个密钥。有两种方法可以做到这一点:侵入式和非侵入式。

侵入性

让Concept&lt;U,T&gt;继承自Deserializable:

class Deserializable
{
    public:
        virtual void deserialize(InputStream& s) = 0;
        virtual int getClassId() const = 0;
};

现在,您可以通过使用getClassId() 检索的id 来识别一个类。所以,接下来就是创建一个工厂。在这里,我将使用一个非常简单的std::map 来说明这一点;随意使用更复杂的。

typedef Deserializable* (*createDeserializableType)();
std::map<int,createDeserializableType> factory;

// ...

factory[id1] = &createMyClass;
// etc...

// ...

// On deserialization
createDeserializable create = factory[idReadFromStream];
if(create)
    create()->deserialize(input_stream);

这意味着要么你必须为Deserializable添加一个store方法,要么你为Deserializable添加一个store方法(我个人更喜欢最后一种方法)。

非侵入式

这个想法是在创建和添加键值的同时反序列化它:

typedef void (*deserializeFctType)(InputStream&);
typedef int id_type;
std::map<id_type,deserializeFctType> factory;

deserialize 方法将在创建后立即存储反序列化类型。

您的问题中不清楚的是接受列表的列表是有限的还是无限的。只有有限的类型集是“容易”序列化的。

【讨论】:

  • 好答案,正是我要建议的(所以现在,我不是):)
猜你喜欢
  • 1970-01-01
  • 2012-11-30
  • 2010-09-19
  • 1970-01-01
  • 1970-01-01
  • 2012-02-13
  • 1970-01-01
相关资源
最近更新 更多