zoukankan      html  css  js  c++  java
  • C# 序列化与反序列化之DataContract与xml对子类进行序列化的解决方案

    C# 序列化与反序列化之DataContract与xml对子类进行序列化的解决方案

    1、DataContract继承对子类进行序列化的解决方案

    第一种是在 [DataContract, KnownType(typeof(继承的子类))]添加 KnownType(typeof(继承的子类))即可,

    第二种是在序列化的时候,添加类型
    DataContractSerializer dcs = new DataContractSerializer(typeof(T),new Type[] { typeof(继承的子类1), typeof(继承的子类1) })
    
    
    using System.Runtime.Serialization;
    
    namespace SupremeConsole
    {
        /// <summary>
        ///  测试类,该类必未标记为可序列化,DataContractJsonSerialize,XmlSerialize可以正常序列化
        /// </summary>
        //继承TestClass的子类SubTestClass的序列化
        //[DataContract, KnownType(typeof(继承的子类)), KnownType(typeof(继承的子类1))]//KnownType指明了,继承子类的序列化的类型如 KnownType(typeof(SubTestClass)),或者再序列化的时候添加子类类型DataContractSerializer dcs = new DataContractSerializer(typeof(T),new Type[] { typeof(继承的子类1), typeof(继承的子类1) }),如:typeof(SubTestClass);
        [DataContract] //如果类型加了DataContract特性标记,而成员字段没有加DataMember特性标记的话,只有类型会序列化,成员不会序列化
        public class TestClass
        {
            /// <summary>
            /// 编号
            /// </summary>
           [DataMember] public int Id { get; set; }
    
            /// <summary>
            /// 姓名
            /// </summary>
            [DataMember] public string Name { get; set; }
    
            /// <summary>
            /// 年龄
            /// </summary>
            [DataMember] public int Age { get; set; }
    
            /// <summary>
            /// 地址
            /// </summary>
            [DataMember] public string Address { get; set; }
    
            /// <summary>
            /// 性别
            /// </summary>
            [DataMember] public string Sex { get; set; }
    
            public override string ToString()
            {
                //return string.Format("编号:{0},姓名:{1},年龄:{2},地址:{3},性别:{4}", Id, Name, Age, Address, Sex);
                return $"编号:{Id},姓名:{Name},年龄:{Age},地址:{Address},性别:{Sex}";
            }
        }
    }

    继承TestClass的子类

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Runtime.Serialization;
    using System.Text;
    using System.Threading.Tasks;
    
    namespace SupremeConsole
    {
        /// <summary>
        /// 继承TestClass的子类
        /// </summary>
        [DataContract]
        public class SubTestClass : TestClass
        {
            /// <summary>
            /// 测试姓名
            /// </summary>
            [DataMember] public string SubTestClassName { get; set; }
        }
    }

    2、xml对继承子类进行序列化的解决方案

    第一种:[XmlInclude(typeof(继承的子类1))],添加 XmlInclude(typeof(继承的子类1))即可,如 XmlInclude(typeof(XmlStudent))

    第二种:序列化的时候添加子类类型XmlSerializer xs = new XmlSerializer (typeof (XmlPerson),new Type[] { typeof (继承的子类1), typeof (继承的子类2)} );,如:new Type[] { typeof (XmlStudent), typeof (XmlTeacher)}

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.Threading.Tasks;
    using System.Xml.Serialization;
    
    namespace SupremeConsole
    {
        /// <summary>
        /// xml序列化测试类
        /// </summary>
        //继承XmlPerson的子类XmlStudent,XmlTeacher的序列化
        //[XmlInclude(typeof(继承的子类1))]//XmlInclude指明了,继承子类的序列化的类型,如 XmlInclude(typeof(XmlStudent)),或者再序列化的时候添加子类类型XmlSerializer xs = new XmlSerializer (typeof (XmlPerson),new Type[] { typeof (继承的子类1), typeof (继承的子类2)} );,如:new Type[] { typeof (XmlStudent), typeof (XmlTeacher)};
        [XmlRoot("haha")]
        //[XmlInclude(typeof(XmlStudent))]
        //[XmlInclude(typeof(XmlTeacher))]
        public class XmlPerson
        {
            /// <summary>
            /// 姓名
            /// </summary>       
            [XmlElement("MyName", Order = 2)]
            public string Name { get; set; }
    
            /// <summary>
            /// 年龄
            /// </summary>       
            [XmlAttribute("MyAge")]
            public int Age { get; set; }
    
            /// <summary>
            /// 住址
            /// </summary>
            [XmlElement("Residence", Order = 1)]
            public string Address { get; set; }
        }
        [XmlType("SubXmlPersonIsXmlStudent")]//XmlStudent序列化后的名称
        public class XmlStudent : XmlPerson
        {
            /// <summary>
            /// 学号
            /// </summary>
            public string StuNumber { get; set; }
        }
    
        [XmlType("SubXmlPersonIsXmlTeacher")]//XmlTeacher序列化后的名称
        public class XmlTeacher : XmlPerson
        {
            /// <summary>
            /// 工号
            /// </summary>
            public string TeachNumber { get; set; }
    
        }
    C# 序列化与反序列化之DataContract与xml对子类进行序列化的解决方案,就是利用特性和序列化的时候指明类型即可

    总结:
    DataContract子类序列化:特性[DataContract, KnownType(typeof(继承的子类)), KnownType(typeof(继承的子类1))]//KnownType指明了,继承子类的序列化的类型如 KnownType(typeof(SubTestClass)),或者再序列化的时候添加子类类型DataContractSerializer dcs = new DataContractSerializer(typeof(T),new Type[] { typeof(继承的子类1), typeof(继承的子类1) }),如:typeof(SubTestClass);
    xml子类序列化:特性[XmlInclude(typeof(继承的子类1))]//XmlInclude指明了,继承子类的序列化的类型,如 XmlInclude(typeof(XmlStudent)),或者再序列化的时候添加子类类型XmlSerializer xs = new XmlSerializer (typeof (XmlPerson),new Type[] { typeof (继承的子类1), typeof (继承的子类2)} );,如:new Type[] { typeof (XmlStudent), typeof (XmlTeacher)};

    测试代码:
    using log4net;
    using System;
    using System.Data;
    using System.Data.SQLite;
    using System.Diagnostics;
    using System.IO;
    using System.IO.Compression;
    using System.IO.MemoryMappedFiles;
    using System.IO.Pipes;
    using System.Linq;
    using System.Net;
    using System.Security.AccessControl;
    using System.Security.Principal;
    using System.Text;
    using System.Threading;
    using System.Threading.Tasks;
    using System.Xml;
    using System.Xml.Serialization;
    using System.Reflection;
    using System.ServiceModel;
    using System.ServiceModel.Channels;
    using System.Runtime.Serialization;
    
    namespace SupremeConsole
    {
        class Program
        {
           
            static void Main(string[] args)
            {
                
                TestSeri();
                Console.ReadLine();
            }
    
           
            public static void TestSeri()
            {
                //Team team = new Team { TName="123",PlayerList = { new Person { Name="1",Age=1},new Person { Name = "2", Age = 2 } } };
                #region BinarySerialize 必须添可序列化属性,即要序列化的对象必须添加SerializableAttribute属性,[Serializable]
                //string s = SerializeManager.Instance.BinarySerialize<Team>(team);//序列化
                //Console.ForegroundColor = ConsoleColor.Green;
                //Console.WriteLine("测试序列化成功。。。");
                //Console.WriteLine($"测试序列化结果:
    {s}");
    
                //string path = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "序列化11111.bin");//序列化
                //SerializeManager.Instance.BinarySerialize<Team>(team, path);
    
                //string path = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "序列化11111.bin");
                //Team test = SerializeManager.Instance.BinaryDeserialize<Team>(path);//反序列化
                //if (test != null)
                //{
                //    Console.WriteLine($"测试序列化结果:{test.ToString()}");
                //}
                #endregion
    
                #region SoapSerialize 必须添可序列化属性,即要序列化的对象必须添加SerializableAttribute属性,[Serializable]
                //string s = SerializeManager.Instance.SoapSerialize<Team>(team);//序列化
                //Console.ForegroundColor = ConsoleColor.Green;
                //Console.WriteLine("测试序列化成功。。。");
                //Console.WriteLine($"测试序列化结果:
    {s}");
    
                //string path = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "Soap序列化.xml");//序列化
                //SerializeManager.Instance.SoapSerialize<Team>(team, path);
    
    
                //string path = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "Soap序列化.xml");
                //Team test = SerializeManager.Instance.SoapDeserialize<Team>(path);//反序列化
                //if (test != null)
                //{
                //    Console.WriteLine($"测试序列化结果:{test.ToString()}");
                //}
                #endregion
    
                #region XmlSerialize 要序列化的对象可以不添加SerializableAttribute属性,[Serializable]
                XmlPerson xmlPerson = new XmlPerson { Name = "1111", Age = 12,Address="住址。。。。" };
                //XmlPerson xmlPerson = new XmlPerson { Name = "1111", Age = 12, HomeAddress = new USAddress { Street = "默默大街三号", PostCode = "233664", Neighbor="邻居666" } };
                string s = SerializeManager.Instance.XmlSerialize<XmlPerson>(xmlPerson);//序列化
                Console.ForegroundColor = ConsoleColor.Green;
                Console.WriteLine("测试序列化成功。。。");
                Console.WriteLine($"测试序列化结果:
    {s}");
    
                //string path = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "序列化.txt");//序列化
                //SerializeManager.Instance.XmlSerialize<TestClass>(testClass, path);
    
                //备用
                //string json = "{"Address":"中国南京","Age":10,"Id":1,"Name":"张三","Sex":"男"}";
                //TestClass test = SerializeManager.Instance.DataContractJsonDeserializeJson<TestClass>(json);//反序列化
                //if (test != null)
                //{
                //    Console.WriteLine($"测试序列化结果:{test.ToString()}");
                //}
    
                //string path = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "序列化.txt");
                //TestClass test = SerializeManager.Instance.XmlDeserialize<TestClass>(path);//反序列化
                //if (test != null)
                //{
                //    Console.WriteLine($"测试序列化结果:{test.ToString()}");
                //} 
                #endregion
            }
    } }
  • 相关阅读:
    面向对象之类属性、类方法,静态方法
    python面向对象之继承
    python之面向对象练习
    python面向对象
    CentOS7.5最小化安装之后的配置
    怎么在一台电脑上安装win7与centos7双系统
    安装Win7时删除系统保留的100M隐藏分区
    win7在安装时跳过输入用户名界面,直接开启管理员用户
    ESP8266 wifi干扰钓鱼实现
    ESP8266 wifi干扰、钓鱼实现
  • 原文地址:https://www.cnblogs.com/1175429393wljblog/p/12035084.html
Copyright © 2011-2022 走看看