便携式类库:推荐替代[Serializable]

我正在将.NET Framework C#类库移植到可移植类库中。 一个反复出现的问题是如何处理用[Serializable]属性修饰的类,因为该属性不是可移植类库子集的一部分。 可移植类库子集中的序列化功能似乎被DataContractAttribute覆盖。

  • 为了在可移植类库中保留尽可能多的功能,用[DataContract]属性替换[Serializable]是否足够(暗示所有需要序列化的字段和属性都需要用[DataMember]装饰为好)?
  • 什么(如果有的话)将我无法使用这种方法,我可以做的做[Serializable]应用?
  • 有没有一种侵入性的方法?
  • 鉴于使用了[DataContract][DataMember] ,我正在考虑按照以下几行更改代码。 这种方法有没有明显的缺陷? 有没有什么办法可以减少冗长的相同事物?

    #if PORTABLE
        [DataContract]
    #else
        [Serializable]
    #endif
        public class SerializableClass : SerializableBaseClass
        {
           ...
    #if !PORTABLE
            protected SerializableClass(SerializationInfo info, StreamingContext context)
                 : base(info, context)
            {
            }
    #endif
            ...
    #if PORTABLE
            [DataMember]
    #endif
            private Type1 _serializableField;
    
    #if PORTABLE
            [DataMember]
    #endif
            private Type2 SerializableProperty { get; set; }
    
            ...
        }
    

    便携式类库(PCL)现已正式弃用 [2017年8月16日]

    如果您今天在不同的.NET实现之间共享代码,您可能会意识到可移植类库(PCL)。 随着.NET Standard 2.0的发布,我们现在正式废弃PCL,您应该将项目移至.NET Standard。

    来源:宣布.NET标准2.0

    便携式类库(PCL)现已在所有平台上提供[2013年10月14日]

    在今天发布之前,PCL引用程序集有许可限制,这意味着它们只能在Windows上使用。 在今天的发布中,我们宣布推出PCL参考组件的新独立版本,其许可证允许它在任何平台上使用 - 包括非微软平台。 这使得开发人员可以更灵活地使用.NET来完成伟大的事情。

    来源:现在可在所有平台上使用可移植类库(PCL)

    下载: Microsoft .NET Portable Library Reference Assemblies 4.6 RC

    仅供参考,允许的一组程序是:

    mscorlib.dll中

    System.dll中

    System.Core.dll

    system.xml.dll的

    System.ComponentModel.Composition.dll(MEF)

    System.Net.dll

    System.Runtime.Serialization.dll

    System.ServiceModel.dll

    System.Xml.Serialization.dll

    System.Windows.dll(来自Silverlight)

    据我所知,您需要使用DataMember属性标记字段,并添加DataContract属性。

    UPDATE

    是。

    你可以看看Json.NET可移植类库解决方案是如何实现的。 当您从这里下载项目Json.NET 4.5 Release 10(source + binary)时,您可以在Source Src Newtonsoft.Json.Portable中找到解决方案。

    基本上他们正在使用自定义属性提供程序的方法

    //不要使用Serializable

    #if !(SILVERLIGHT || WINDOWS_PHONE || NETFX_CORE || PORTABLE)
      [Serializable]
    #endif
    

    //使用自定义提供者

    #if NETFX_CORE || PORTABLE
    using ICustomAttributeProvider = Newtonsoft.Json.Utilities.CustomAttributeProvider;
    #endif 
    

    如果项目是便携式的

    #if !PocketPC && !NET20
          DataContractAttribute dataContractAttribute = GetDataContractAttribute(objectType);
          if (dataContractAttribute != null)
            return MemberSerialization.OptIn;
    #endif
    

    OptIn描述为:

     /// <summary>
        /// Only members must be marked with <see cref="JsonPropertyAttribute"/> or <see cref="DataMemberAttribute"/> are serialized.
        /// This member serialization mode can also be set by marking the class with <see cref="DataContractAttribute"/>.
        /// </summary>
        OptIn,
    

    希望能帮助到你。

    更新2

    我是否会失去使用[DataContract]而不是[Serializable]的能力,或者我仍然能够完成[Serializable]支持的所有功能?

    您可以完成Serializable支持的所有功能,除了控制设置名称和顺序之外的对象是如何序列化的。

    使用DataContractSerializer有几个好处:

    序列化用[DataMember]装饰的任何东西,即使它不公开可见

    不能序列化任何东西,除非你明确地告诉它(“选择加入”)

    您可以使用[DataMember]上的[DataMember] [Order=]属性定义元素序列化的[Order=]

    不需要用于反序列化的无参数构造函数

    比XmlSerializer快10%。

    在这里阅读更多:XmlSerializer与DataContractSerializer

    另供参考:

    DataContract支持在默认模式下对以下类型的类型进行序列化:CLR内置类型

    字节数组,DateTime,TimeSpan,GUID,Uri,XmlQualifiedName,XmlElement和XmlNode数组

    枚举

    标有DataContract或CollectionDataContract属性的类型

    实现IXmlSerializable的类型

    数组和集合类包括List,Dictionary和Hashtable

    标有Seri​​alizable属性的类型包括那些实现ISerializable的类型

    没有上述属性(POCO)但具有默认构造函数的类型


    你可以做的一件事是消除常量预处理器指令引起的混乱,就是将它推到一个新的SerializableAttribute类中,并基本上欺骗编译器。

    #if PORTABLE
    namespace System
    {
       public class SerializableAttribute : Attribute
       {
           //this does nothing
       }  
    }
    #endif
    

    然后继续用正常的Serializable来装饰你的类。


    对于.Net 4.6以上的版本,DataContract不再可用于PCL。 你需要在这里添加Nuget包System.Runtime.Serialization.Primitives:https://www.nuget.org/packages/System.Runtime.Serialization.Primitives/

    注意实际的序列化,你可能还需要一个实现,比如System.Runtime.Serialization.Json,System.Runtime.Serialization.Xml或Newtonsoft.Json。

    链接地址: http://www.djcxy.com/p/68851.html

    上一篇: Portable class library: recommended replacement for [Serializable]

    下一篇: Portable Class Library equivalent to MethodBase.GetCurrentMethod