c# XML序列化——削弱封装

本文关键字:封装 序列化 XML | 更新日期: 2023-09-27 18:15:53

我认为正确吗,为了让c#序列化一个对象,我必须有一个公共属性的每个字段,需要它的状态存储?

如果是这样,是不是非常非常糟糕,因为它削弱(如果不是完全破坏)我的类的任何封装?

在Java中,XStream可以遍历每个非瞬态字段并将其归档。在c#中,这是不可能发生的,而且更糟糕的是,字典之类的东西根本不序列化。这里有点乱,不是吗?

我已经看到了XStream到。net"端口"的DLL,但是没有文档,我很怀疑。

c# XML序列化——削弱封装

您应该使用DataContractSerializer,并标记您想要用[DataMember]序列化的每个属性/字段。它不关心您的字段是私有的还是公共的。顺便说一下,你可以用它序列化字典…

[DataContract]
public class MyClass
{
    [DataMember]
    private string _privateField;
    [DataMember]
    public int PublicProperty { get; set;}
}
序列化:

private static string SerializeXml<T>(T item)
{
    DataContractSerializer ser = new DataContractSerializer(item.GetType());
    StringBuilder sb = new StringBuilder();
    XmlWriterSettings settings = new XmlWriterSettings { OmitXmlDeclaration = true, ConformanceLevel = ConformanceLevel.Fragment };
    using (XmlWriter writer = new XmlWriter(sb, settings))
    {
        ser.WriteObject(writer, item);
    }
    return sb.ToString();
}

查看XmlSerializer和DataContractSerializer之间的差异:http://www.danrigsby.com/blog/index.php/2008/03/07/xmlserializer-vs-datacontractserializer-serialization-in-wcf/

binaryformatter序列化私有甚至只读字段,而不需要属性。XmlSerializer只能使用公共无参数构造函数和公共属性进行序列化。如果希望使用带有封装的XmlSerializer,可以使用IXmlSerializable,但这相当麻烦。

如果你的对象模型相当简单,或者你可以通过引入特殊的DTO:s来实现序列化(例如避免结构体),那么我建议使用基于契约的序列化器,它可以序列化私有字段或属性。看看protobuf-net。