.net 什么是对象图以及如何序列化一个对象图
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/877157/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
What is an object graph and how do I serialize one
提问by pkolodziej
I've been reading lately about serialization. I've read that when I use XmlSerialization I cannot serialize object graphs. What is an object graph and why I cannot serialize it simply?
我最近一直在阅读有关序列化的文章。我读过当我使用 XmlSerialization 时,我无法序列化对象图。什么是对象图,为什么我不能简单地序列化它?
回答by Marc Gravell
An object graph is not a single object, but rather a set of related objects. For a simple example, consider:
对象图不是单个对象,而是一组相关对象。举一个简单的例子,考虑:
public class Node {
public string Name {...}
public Node Parent {...}
public List<Node> Children {...}
}
where each child knows about the parent (and the parent knows about the child).
每个孩子都知道父母的情况(父母也知道孩子)。
The problem is that xml is a tree based on object properties... and it wants to just walk them - i.e. with the simple parent/child:
问题是 xml 是基于对象属性的树......它只想遍历它们 - 即使用简单的父/子:
- A (knows that B is its child)
- B (knows that A is its parent)
- A(知道 B 是它的孩子)
- B(知道 A 是它的父级)
that would serialize as:
这将序列化为:
<Node>
<Name>A</Name>
<!-- no Parent as A is the top node, so null -->
<Children>
<Node>
<Name>B</Name>
<Parent>
<Node>
<Name>A</Name>
*** boom ***
You can see that we got back to A, so we're now in an endless loop.
你可以看到我们回到了 A,所以我们现在处于无限循环中。
XmlSerializercan serialize treesof data, but not full graphs. You can mark properties to be ignored, for example:
XmlSerializer可以序列化数据树,但不能序列化完整图。您可以标记要忽略的属性,例如:
[XmlIgnore]
public Node Parent {...}
And now it'll work, but we'll have to fix the Parentafterwards.
现在它会起作用,但我们必须在Parent之后修复它。
By contrast, some other serializers can handle graphs (DataContractSerializercan on-demand). It does this by tracking objects against a unique key - but then the output isn't what you expect from regular xml.
相比之下,其他一些序列化程序可以处理图形(DataContractSerializer可以按需)。它通过根据唯一键跟踪对象来实现这一点 - 但是输出不是您对常规 xml 所期望的。
回答by Andrew Shepherd
An object graph is a set of objects that reference one another.
对象图是一组相互引用的对象。
Serializing an object graph is tricky. The serializer would have to assign a unique ID to every object and then replace references with unique IDs.
序列化对象图很棘手。序列化程序必须为每个对象分配一个唯一的 ID,然后用唯一的 ID 替换引用。
If it was serializing in XML format, and handling object graphs, it would have to add an "OBJECT_ID" (or some other named) attribute to every element. This would be very easy to break: what would happen if you added a property with the same name to the class you are serializing?
如果它以 XML 格式序列化并处理对象图,则必须向每个元素添加“OBJECT_ID”(或其他命名的)属性。这很容易被破坏:如果向正在序列化的类添加同名的属性会发生什么?
The simplest solution is to not support it.
最简单的解决方案是不支持它。
.NET provides binary serialization which deals with this issue as well as the issue of circular references.
.NET 提供了二进制序列化来处理这个问题以及循环引用的问题。
回答by Pontus Gagge
A general object graphconsists of a set of object holding references to each other. If you have an object tree where there are no backwards links, serialization and deserialization is simple. With a general graph, the (de)serialization process needs to keep track of the identity of each object, and use some form of mark-and-sweep algorithm to ensure that objects aren't (de)serialized twice.
一个通用的对象图由一组保存彼此引用的对象组成。如果您有一个没有反向链接的对象树,序列化和反序列化很简单。对于通用图,(反)序列化过程需要跟踪每个对象的身份,并使用某种形式的标记和清除算法来确保对象不会(反)序列化两次。

