序列化私有成员数据

Jon*_*ell 73 .net c# xml serialization serializable

我正在尝试将对象序列化为具有许多属性的XML,其中一些属性是只读的.

public Guid Id { get; private set; }
Run Code Online (Sandbox Code Playgroud)

我已经标记了类[Serializable],我已经实现了ISerializable接口.

下面是我用来序列化对象的代码.

public void SaveMyObject(MyObject obj)
{
    XmlSerializer serializer = new XmlSerializer(typeof(MyObject));
    TextWriter tw = new StreamWriter(_location);
    serializer.Serialize(tw, obj);
    tw.Close();
}
Run Code Online (Sandbox Code Playgroud)

不幸的是,它会在第一行显示此消息.

InvalidOperationException未处理:无法生成临时类(result = 1).错误CS0200:无法将属性或索引器"MyObject.Id"分配给 - 它是只读的

如果我将Id属性设置为public,则可以正常工作.有人可以告诉我,如果我正在做某事,或者至少是否可能吗?

Mar*_*ell 61

您可以使用DataContractSerializer(但请注意,您不能使用xml属性 - 只能使用xml元素):

using System;
using System.Runtime.Serialization;
using System.Xml;
[DataContract]
class MyObject {
    public MyObject(Guid id) { this.id = id; }
    [DataMember(Name="Id")]
    private Guid id;
    public Guid Id { get {return id;}}
}
static class Program {
    static void Main() {
        var ser = new DataContractSerializer(typeof(MyObject));
        var obj = new MyObject(Guid.NewGuid());
        using(XmlWriter xw = XmlWriter.Create(Console.Out)) {
            ser.WriteObject(xw, obj);
        }
    }
}
Run Code Online (Sandbox Code Playgroud)

或者,你可以IXmlSerializable自己实现并完成所有事情 - 但XmlSerializer至少可以这样做.

  • 这对我有用,但后来我发现使用DataMemberAttribute序列化私有成员只能在完全信任环境中运行,而不是部分信任.解决方案是使成员内部而不是私有.有关详细信息,请参阅http://blog.walteralmeida.com/2010/05/wcf-and-datacontract-serialization-internals-and-tips-.html. (4认同)

Ste*_*ger 6

你可以使用System.Runtime.Serialization.NetDataContractSerializer.它功能更强大,修复了经典Xml Serializer的一些问题.

请注意,此属性有不同的属性.

[DataContract]
public class X
{
  [DataMember]
  public Guid Id { get; private set; }
}


NetDataContractSerializer serializer = new NetDataContractSerializer();
TextWriter tw = new StreamWriter(_location);
serializer.Serialize(tw, obj);
Run Code Online (Sandbox Code Playgroud)

编辑:

根据Marc的评论进行更新:您可能应该System.Runtime.Serialization.DataContractSerializer根据自己的情况使用干净的XML.其余的代码是一样的.