C#:将对象序列化为XML而不进行反射

时间:2014-02-13 11:29:37

标签: c# xml linq serialization reflection

在应用程序中,我们可以保存应用程序的当前状态及其配置(可能很大)。我们正在使用XmlSerializer

我们现在只需要XML中的所有内容(所有XmlIgnore都已到位),并且存储整个配置(文件大约为50-100MB)非常慢。

我们需要继续将此配置存储为XML,但我们希望避免:

  • 反射,慢慢
  • 实施IXmlSerializable界面

我们的想法是在每个对象中实现一个方法,我们可以在其中注册我们想要序列化的字段/属性,然后使用SerializationManager来读取我们想要序列化的内容,以及然后写下来。

像这样,对象不知道它们将被呈现的语言(XML),如果有一天我们想要二进制序列化(或者如果我们想要以不同的格式序列化),我们可以

但是我们不想重新发明轮子,我不知道是否存在某些库,或者像Linq to xml这样的东西可以提供帮助,或者这本身是否可行,......

那你怎么认为我能做到这一点?

2 个答案:

答案 0 :(得分:4)

“反思,慢下来”

除此之外,它不会在运行时使用反射。它在第一次运行时执行元编程(假设您使用new XmlSerializer(type))来检查类型并生成将在给定类型上工作的静态代码。因此,任何与卷相关的性能问题都与反射无关。 有可能元编程本身可以花费可测量的时间,但是:除非你的模型真的复杂,否则这是不太可能的,并且b :可以使用sgen.exe工具预生成序列化程序集来避免这种情况。

因此,任何性能问题很可能是由于模型的大小和xml的开销。

如果您想尝试不同的序列化程序,请考虑使用protobuf-net。您将无法读取数据(它不会是xml),但输出会更小更快。

答案 1 :(得分:0)

如你所说

  

在应用程序中,我们可以保存应用程序的当前状态,并且配置

状态,特别是当它很大(100Mb是......巨大的!)时,需要自己的方式来序列化数据。我们中的许多人都知道并且讨厌过去节省/加载游戏的速度慢。即使是现在,游戏开发人员也会将 quicksave 与序数保存区分开来。它被优化为比顺序保存更快(例如,通过缓存最近执行的快速保存的一部分)。

第一个问题是XML的原因? BinarySerializer更快,但对于这样的大小,你最好使用手动序列化(正如Marc Gravell建议的那样,使用protobuf,它最终优于任何东西)。

第二个问题是,您真的需要序列化数据(更改其格式)吗?保存状态的最快方法是转储内存。想象一下,您将所有数据保存在一个内存块中,然后将此块转储到文件中是一个非常快速的保存。您可能(我不确定,但它应该是可行的)以某种方式构建您的数据,覆盖此内存将是一种加载游戏。任何转换都要快得多。

如果您使用转储,请考虑将其打包(放入zip)。打包和保存10 mb应该比保存解压缩100 mb快(假设你没有使用太慢或太好的打包算法),内存操作和CPU比SSD快得多。

要保存配置,您仍可以照常将其序列化。如果您希望它是单个文件,则定义此文件的自己的格式,例如:

config_stream, separator["<<<>>>>"], memory block [100 Mb]

XmlSerializer序列化到内存中,创建文件,保存配置,分隔符,转储。