为什么XML-Serializable类需要一个无参数的构造函数

我在写代码来做Xml序列化。 具有以下function。

public static string SerializeToXml(object obj) { XmlSerializer serializer = new XmlSerializer(obj.GetType()); using (StringWriter writer = new StringWriter()) { serializer.Serialize(writer, obj); return writer.ToString(); } } 

如果参数是没有无参数构造函数的类的实例,则会抛出exception。

未处理的exception:System.InvalidOperationException:CSharpConsole.Foo不能被序列化,因为它没有无参数的构造函数。 System.Xml.Serialization.Type.Class.Model上的System.Xml.Serialization.TypeDesc.CheckSupported()在types,成员信息源,布尔directReference, (System.Xml.Serialization.XmlReflectionImporter.ImportTypeMapping(typestypes,XmlRootAttribute根,stringdefaultNamespace)在System.Xml.Serialization.XmlSerializer..ctor(typestypes,stringdefaultName空间)在System.Xml.Serialization。 XmlSerializer..ctor(typestypes)

为什么必须有一个无参数的构造函数才能让xml序列化成功呢?

编辑:感谢cfeduke的答案。 无参数的构造函数可以是私有的或内部的。

在对象的反序列化过程中,负责解序列化对象的类将创build序列化类的实例,然后仅在获取要填充的实例后继续填充序列化的字段和属性。

如果你愿意,你可以使你的构造函数是privateinternal ,只要它没有参数就可以。

这是XmlSerializer的限制。 请注意, BinaryFormatterDataContractSerializer 不需要这样做 – 它们可以创build一个未初始化的对象,并在反序列化过程中对其进行初始化。

由于您使用的是XML,因此您可能会考虑使用DataContractSerializer并使用[DataContract] / [DataMember ]标记您的类,但请注意,这会更改模式(例如,没有[XmlAttribute]等同物 – 所有内容都变为元素)。

更新:如果你真的想知道, BinaryFormatter等人使用FormatterServices.GetUninitializedObject()来创build对象,而无需调用构造函数。 可能危险; 我不build议使用它太频繁; – p另请参阅MSDN上的评论:

因为对象的新实例初始化为零,并且没有构造函数运行,所以该对象可能不会表示该对象认为有效的状态。 当用户打算立即填充所有字段时,只应该使用当前的方法进行反序列化。 它不会创build一个未初始化的string,因为创build一个不可变types的空实例是没有用的。

我有我自己的序列化引擎,但我不打算使用FormatterServices ; 我很想知道构造函数( 任何构造函数)实际上已经执行。

首先,这是用文档写的。 我认为这是你的一个类的领域,而不是主要的领域之一 – 你想如何反序列化器构造它返回W / O无参数构造?

我认为有一个解决方法,使构造私人。