【问题标题】:command pattern serialization in c++C++中的命令模式序列化
【发布时间】:2011-07-11 09:26:07
【问题描述】:

我想在 C++ 中执行以下操作:

  1. 创建命令对象
  2. 序列化
  3. (将其发送到另一台计算机)
  4. 反序列化
  5. 执行

两种情况:

  • 发送者和接收者都是win 7 电脑
  • 发件人是*nix,收件人是win 7

我找到了一个序列化教程:http://www.functionx.com/cpp/articles/serialization.htm。这是要走的路吗?在 python 中我可以这样做:

def setAndPackCommand(self, object):
    outFile = StringIO.StringIO()
    pickledC = pickle.dump(object, outFile) # this packs object to outFile
    stringToSend = outFile.getvalue() # decoding to string

def unpackAndExecute(self, stringToReceive):
    inFile = StringIO.StringIO()
    inFile.write(stringToReceive)
    inFile.seek(0, 0)
    receivedC = pickle.load(inFile)     
    receivedC.execute()

在这段代码中,重点是pickle.dump 和pickle.load。什么是 C++ 对应物?维基百科说c++不支持序列化?那么上面的链接是什么?

二进制序列化是什么意思?内存被转储到磁盘并且反序列化需要完全相同的计算机(没有跨平台传输)?

br, 朱哈

【问题讨论】:

    标签: c++ serialization command-pattern


    【解决方案1】:

    我还建议使用像 boost.serialization 这样的稳定​​库来序列化数据。

    如果您不熟悉序列化,这意味着将对象转换为适合传输或存储的数据表示,然后从该数据表示中重建它们。所谓的PODs (Plain Old Data objects),难度并不大。您可以将缓冲区作为数据传输并在传输后通过注意data alignmentbyte ordering(字节序)将其转换回。如果对象引用其他对象会变得更加复杂,那么使用设计良好的库就很有意义。 Boost 的序列化还支持版本控制,因此您可以更新格式并保持向后兼容的阅读器和编写器(当然要付出一些努力)

    Here is a good introduction.

    【讨论】:

    • 序列化不一定与传输串行通信有任何关系。这对于将对象状态保存到磁盘以在以后恢复同样有用。
    • @Mac,谢谢。提供的定义是废话而且非常模糊,除了表述不当。我换了一个更好的。
    【解决方案2】:

    为了简要回答您的问题,维基百科是对的 - C++ 本机不支持序列化。这并不意味着您不能推出自己的解决方案,尽管如您链接的文章中所示。

    二进制序列化是指将对象写入二进制文件格式。与(例如)将对象写入基于 XML 格式的 XML 序列化进行对比:在前者中,您将获得一个二进制文件,其中(例如)int 由 4 个字节的原始二进制数据组成。在后者中,您可能会得到一个带有name 属性的int 标记,其内容是整数的文本值,例如<int name="myInt">12345</int>

    二进制序列化的最大优点是(在大多数情况下)它非常紧凑,并且在目标平台上与对象之间相互转换非常简单。缺点是,正如您所建议的,它往往是非常特定于机器的,因此在您的情况下不是很有用。字节顺序和字段对齐等问题往往因平台而异,因此未考虑这些问题的二进制格式很可能无法移植。也就是说,您可以添加代码来考虑这些差异,但这确实会增加解决方案的复杂性。

    替代方案(基于文本的序列化、XML 序列化等)具有通常更跨平台且更易于手动编辑的优势,但通常不如二进制方法紧凑。

    由于上述原因,我会避免在您的情况下进行二进制序列化(如果可能),并采用基于文本的方法。我喜欢的一篇文章是this one,它描述了(除其他外)一种序列化方法,可让您轻松指定您喜欢使用的任何类型的序列化方法。

    【讨论】:

    • 这种序列化方法与微软为其MFC框架创建的序列化方法非常相似。
    【解决方案3】:

    当然 C++ 程序可以进行序列化,只是不是开箱即用。查看 Boost.Serialization 库或 Google 的 protocol buffers。后者实现了快速且可移植的跨平台(二进制)序列化,但它需要使用代码生成器。

    (您链接到的教程演示了一种非常简单、不可移植的序列化方法。它还很好地演示了 not 如何在 C++ 中处理字符串。)

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2015-01-13
      • 1970-01-01
      • 2013-11-26
      • 2019-01-10
      • 2013-02-22
      • 2016-07-12
      • 2012-04-30
      • 1970-01-01
      相关资源
      最近更新 更多