原文 www.cnblogs.com/mgen/archive/2011/12/03/2275014.html

注意:

运行代码请注意添加如下命名空间:

using System.Xml;

using System.Xml.Serialization;

using System.IO;

返回目录

1. 针对基类的XmlSerializer序列化派生类

派生类将会序列化成这样的XML:

<基类名称xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"

xmlns:xsd="http://www.w3.org/2001/XMLSchema"

xsi:type="派生类名称">

<!-- 基类和派生类的内容 -->

</基类名称>

第一种方法是在基类添加XmlInclude特性,这样的话基类的XmlSerializer可以序列化派生类了。

代码:

//基类加入XmlInclude

[XmlInclude(typeof(b))]

publicclassa

{

publicint aaa;

}

publicclassb : a

{

publicint bbb;

}

classProgram

{

staticvoid Main()

{

var xs =newXmlSerializer(typeof(a));

using (var textWriter =newStringWriter())

{

xs.Serialize(textWriter, newb());

Console.WriteLine(textWriter);

}

}

}

输出XML:

<axmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"

xmlns:xsd="http://www.w3.org/2001/XMLSchema"

xsi:type="b">

</aaa>

</bbb>

</a>

第二种方法就是在XmlSerializer的构造函数内指定派生类型,然后序列化,这样就不用在基类上加入XmlInclude特性了。

代码:

//无需加入XmlInclude

publicclassa

{

publicint aaa;

}

publicclassb : a

{

publicint bbb;

}

classProgram

{

staticvoid Main()

{

var xs =newXmlSerializer(typeof(a), newType[] { typeof(b) });

using (var textWriter =newStringWriter())

{

xs.Serialize(textWriter, newb());

Console.WriteLine(textWriter);

}

}

}

输出和上面一样!

返回目录

2. 类内成员是派生类的序列化

还是上面的类a和b,现在再加入一个c类,这个c类中有一个a的对象:

publicclassa

{

publicint aaa;

}

publicclassb : a

{

publicint bbb;

}

publicclassc

{

publica objA =newa();

}

此时直接XML序列化一个c对象,结果是这样的XML:

<cxmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"

xmlns:xsd="http://www.w3.org/2001/XMLSchema">

<objA>

</aaa>

</objA>

</c>

下面搞得复杂些,把c中的a对象改成这样:

publicclassc

{

publica objA =newb();

}

此时仿佛又回到了文章第一个标题,如果直接序列化c的话,会抛出异常。那么按照上面第一个方法,先在a上加入XmlInclude特性,然后再序列化c对象。

全部代码:

[XmlInclude(typeof(b))]

publicclassa

{

publicint aaa;

}

publicclassb : a

{

publicint bbb;

}

publicclassc

{

publica objA =newb();

}

classProgram

{

staticvoid Main()

{

var xs =newXmlSerializer(typeof(c));

using (var textWriter =newStringWriter())

{

xs.Serialize(textWriter, newc());

Console.WriteLine(textWriter);

}

}

}

输出XML(根节点c省略):

<objAxsi:type="b">

</aaa>

</bbb>

</objA>

和标题1的第一个方法类似!

但是标题1的第二个方法在这里没法使用的,因为c类和b类没有任何继承关系,在针对c的XmlSerializer不可能加入b的类型。这里其实还 有一种方法,加入XmlElement特性,其中ElementName属性是最终的Xml元素名称,而Type属性是针对的类型,这里加入b类型,不过 最好把a类型也加入(因为字段类型是a,有可能被赋值为a的对象)。

全部代码:

//不需要加XmlInclude

publicclassa

{

publicint aaa;

}

publicclassb : a

{

publicint bbb;

}

publicclassc

{

[XmlElement(ElementName ="b", Type =typeof(b))]

[XmlElement(ElementName ="a", Type =typeof(a))]

publica objA =newb();

}

classProgram

{

staticvoid Main()

{

var xs =newXmlSerializer(typeof(c));

using (var textWriter =newStringWriter())

{

xs.Serialize(textWriter, newc());

Console.WriteLine(textWriter);

}

}

}

生成XML:

<cxmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"

xmlns:xsd="http://www.w3.org/2001/XMLSchema">

<b>

</aaa>

</bbb>

</b>

</c>

 

作者:Mgen
出处:www.cnblogs.com/mgen

其他参考页面:我的软件和工程博客导读

.NET(C#):XML序列化时派生类的处理的更多相关文章

  1. c# 中xml序列化时相同节点存入不同类型值

    先上需要序列话的类定义: [System.Xml.Serialization.XmlIncludeAttribute(typeof(DescriptionType))] [System.CodeDom ...

  2. XML序列化反序列化—常用类

    public class XMLSerializer    {        #region (public) xml序列化        /// <summary>        /// ...

  3. 在XML序列化时去除默认命名空间xmlns:xsd和xmlns:xsi

    摘 自: http://blog.csdn.net/fxhflower/article/details/7276820 可使用以下代码: //Create our own namespaces for ...

  4. C#中将xml文件反序列化为实例时采用基类还是派生类的问题

    基类: using System; using System.Collections.Generic; using System.Linq; using System.Text; namespace ...

  5. .NET中XML序列化和反序列化常用类和用来控制XML序列化的属性总结(XmlSerializer,XmlTypeAttribute,XmlElementAttribute,XmlAttributeAttribute,XmlArrayAttribute...)

    序列化和反序列化是指什么? 序列化(seriallization): 将对象转化为便于传输的数据格式, 常见的序列化格式:二进制格式,字节数组,json字符串,xml字符串.反序列化(deserial ...

  6. 关于C# XML序列化的一个BUG的修改

    关于C# XML序列化的一个BUG的修改 在我前一篇博客中提到用XML序列化作为数据库的一个方案,@拿笔小心 提到他们在用XML序列化时,遇到了一个比较严重的bug,即XML不闭合,系统不能正确的加载 ...

  7. Windows phone 之XML序列化与反序列化

    为什么要做序列化和反序列化? 一个回答: 我们都知道对象是不能在网络中直接传输的,不过还有补救的办法.XML(Extensible Markup Language)可扩展标记语言,本身就被设计用来存储 ...

  8. C#操作Xml:XmlSerializer 对象的Xml序列化和反序列化

    这篇随笔对应的.Net命名空间是System.Xml.Serialization:文中的示例代码需要引用这个命名空间. 为什么要做序列化和反序列化? .Net程序执行时,对象都驻留在内存中:内存中的对 ...

  9. Xml 序列化

    1 XML序列化只能序列化对象的公有属性,并且要求对象有一个无参的构造方法,否者无法反序列化. 2 [Serializable]和[NonSerialized]特性对XML序列化无效!所以使用XML序 ...

随机推荐

  1. std::string 字符替换函数

    // 替换路径中所有“\”为“/” #include <algorithm> static std::string ConvertSlash(std::string& strUrl ...

  2. 图片压缩上传 Android

    图片压缩的话 想保持 图像清晰度,但是又想保持图片的大小在100k左右. 同时的话又不想自己写那些压缩的代码的话.那你就找对地方了. 提供一个思路. 先读取你的文件,然后读到bitmap里面进行尺寸裁 ...

  3. css3 drop-shaow阴影效果

    <!DOCTYPE html> <html lang="en"> <head> <meta charset="utf-8&quo ...

  4. 学习笔记(一) HTML+CSS基础课程

    这个周把慕课网的<HTML+CSS基础课程>课程学完,内容都是非常非常基础的,不过还是学到了几个小知识点,记下来先. <a>超链接发送邮件 直接上把他的图片给挪过来了,我就不打 ...

  5. 程序员眼里IE浏览器是什么样的

    主流浏览器之争从上个世纪开就开始,已经持续了很长的时间.就在几年前,IE还是最主流的web浏览器.但现在形势完全不同了,人们都在笑话IE,纷纷转向其它浏览器.今天,我向大家分享一下针对IE的搞笑图片, ...

  6. Delphi中运行时改变panel的位置及大小(WM_SysCommand消息配合参数使用,很奇妙) good

    procedure TForm1.pnl1MouseDown(Sender: TObject; Button: TMouseButton; Shift: TShiftState; X, Y: Inte ...

  7. POJ 2686 Traveling by Stagecoach 壮压DP

    大意是有一个人从某个城市要到另一个城市(点数<=30) 然后有n个马车票,相邻的两个城市走的话要消耗掉一个马车票. 花费的时间呢,是马车票上有个速率值,用边/速率就是花的时间. 问最后这个人花费 ...

  8. poj2388---求奇数个数字的最中间的数

    #include <stdio.h> #include <stdlib.h> int cmp(const void *a,const void *b) { return (*( ...

  9. poj1580---欧几里得算法(辗转相除法)

    #include<stdio.h> #include<string.h> #include<string.h> ],str2[]; int len; int cal ...

  10. 详解Spring中的CharacterEncodingFilter--forceEncoding为true在java代码中设置失效--html设置编码无效

    在项目中有很多让人头疼的问题,其中,编码问题位列其一,那么在Spring框架中是如何解决从页面传来的字符串的编码问题的呢?下面我们来看看Spring框架给我们提供过滤器CharacterEncodin ...