C#.NET解析XML(使用屬性控制 XML 序列化)


使用屬性可以控制對象的 XML 序列化。

默認情況下,XML 元素名稱由類或成員名稱確定。在名為 Book 的簡單類中,字段 ISBN 將生成 XML 元素標記 <ISBN>,如下面的示例所示。

[csharp] view plain copy
public class Book  
{  
    public string ISBN;  
}  
// When an instance of the Book class is serialized, it might   
// produce this XML:  
// <ISBN>1234567890</ISBN>.  

若要重新命名元素,可以更改這種默認行為。下面的代碼演示屬性 (Attribute) 如何通過設置 XmlElementAttribute 的 ElementName 屬性 (Property) 實現此目的。

[csharp] view plain copy
public class TaxRates{  
    [XmlElement(ElementName = "TaxRate")]  
    public decimal ReturnTaxRate;  
}  
 

XmlArrayAttribute 和 XmlArrayItemAttribute 屬性旨在用於控制數組的序列化。使用這些屬性可以控制元素名稱、命名空間以及 XML 架構 (XSD) 數據類型(在萬維網聯合會 [www.w3.org] 文檔“XML 架構第 2 部分:數據類型”中進行了定義)。此外,還可以指定數組所能包含的類型。

對於序列化數組時生成的封閉 XML 元素,其屬性將由 XmlArrayAttribute 確定。例如,默認情況下,序列化下面的數組時,將會生成名為Employees 的 XML 元素。Employees 元素將包含在數組類型Employee 之后命名的一系列元素。

[csharp] view plain copy
public class Group{  
    public Employee[] Employees;  
}  
public class Employee{  
    public string Name;  
}  

序列化實例可能如下所示。

[html] view plain copy
<Group>  
<Employees>  
    <Employee>  
        <Name>Haley</Name>  
    </Employee>  
</Employees >  
</Group>  
 

通過應用 XmlArrayAttribute,可以按照以下方式更改 XML 元素的名稱。

[csharp] view plain copy
public class Group{  
    [XmlArray("TeamMembers")]  
    public Employee[] Employees;  
}  
 

生成的 XML 可能如下所示。

[html] view plain copy
<Group>  
<TeamMembers>  
    <Employee>  
        <Name>Haley</Name>  
    </Employee>  
</TeamMembers>  
 

另一方面,XmlArrayItemAttribute 可以控制如何序列化數組中包含的項。請注意,該屬性將應用於返回數組的字段。

[csharp] view plain copy
public class Group{  
    [XmlArrayItem("MemberName")]  
    public Employee[] Employees;  
}  
 

生成的 XML 可能如下所示。

[html] view plain copy
<Group>  
<Employees>  
    <MemberName>Haley</MemberName>  
</Employees>  
</Group>  

 

序列化派生類
XmlArrayItemAttribute 的另一種用法是,允許序列化派生類。例如,可將派生自 Employee 的另一個名為Manager 的類添加至上一示例中。如果沒有應用XmlArrayItemAttribute,代碼將在運行時失敗,原因是無法識別派生類類型。若要解決這個問題,每次為每個可接受類型(基類和派生類)設置 Type 屬性 (Property) 時,需要應用該屬性 (Attribute) 兩次。

[csharp] view plain copy
public class Group{  
    [XmlArrayItem(Type = typeof(Employee)),  
    XmlArrayItem(Type = typeof(Manager))]  
    public Employee[] Employees;  
}  
public class Employee{  
    public string Name;  
}  
public class Manager:Employee{  
    public int Level;  
}  

 

序列化實例可能如下所示。

[html] view plain copy
<Group>  
<Employees>  
    <Employee>  
        <Name>Haley</Name>  
    </Employee>  
    <Employee xsi:type = "Manager">  
        <Name>Ann</Name>  
        <Level>3</Level>  
    <Employee>  
</Employees >  
</Group>  
將數組作為元素序列進行序列化
通過將 XmlElementAttribute 應用於返回數組的字段,還可以將該數組作為 XML 元素的平面序列進行序列化,如下所示。

[csharp] view plain copy
public class Group{  
    [XmlElement]  
    public Employee[] Employees;  
}  

 

序列化實例可能如下所示。

[html] view plain copy
<Group>  
<Employees>  
    <Name>Haley</Name>  
</Employees>  
<Employees>  
    <Name>Noriko</Name>  
</Employees>  
<Employees>  
    <Name>Marco</Name>  
</Employees>  
</Group>  

 

區別兩種 XML 流的另一個方法是,使用 XML 架構定義工具,從編譯好的代碼生成 XML 架構 (XSD) 文檔文件。沒有將屬性應用於字段時,架構會以下列方式描述元素。

     
<xs:element minOccurs="0" maxOccurs ="1" name="Employees" type="ArrayOfEmployee" />
將 XmlElementAttribute 應用於字段時,生成的架構會以下列方式描述元素。

      
<xs:element minOccurs="0" maxOccurs="unbounded" name="Employees" type="Employee" /> 
序列化 ArrayList
ArrayList 類可能包含各種不同對象的集合。因此,可以按照使用數組的類似方式使用 ArrayList。您可以創建返回單個ArrayList 的字段,而不用創建返回類型化對象的數組的字段。但是,與數組相同的是,必須將ArrayList 包含的對象的類型告知 XmlSerializer。為此,需要為該字段分配XmlElementAttribute 的多個實例,如下面的示例所示。

[csharp] view plain copy
public class Group{  
    [XmlElement(Type = typeof(Employee)),   
    XmlElement(Type = typeof(Manager))]  
    public ArrayList Info;  
}  

 

使用 XmlRootAttribute 和 XmlTypeAttribute 控制類的序列化
能且只能應用於一個類的屬性有下面兩種:XmlRootAttribute 和 XmlTypeAttribute。這兩種屬性非常相似。XmlRootAttribute 只能應用於一個類:序列化時,該類表示 XML 文檔的開始和結束元素,也就是根元素。另一方面,XmlTypeAttribute 可以應用於任何一個類,包括根類。

例如,在上面的示例中,Group 類就是根類,而其所有的公共字段和屬性變成 XML 文檔中的 XML 元素。因此,只能有一個根類。通過應用XmlRootAttribute,可以控制XmlSerializer 所生成的 XML 流。例如,可以更改元素名稱和命名空間。

使用 XmlTypeAttribute 可以控制所生成 XML 的架構。需要通過 XML Web services 發布架構時,這項功能很有用。下面的示例將XmlTypeAttribute 和XmlRootAttribute 同時應用於同一個類。

[csharp] view plain copy
[XmlRoot("NewGroupName")]  
[XmlType("NewTypeName")]  
public class Group{  
    public Employee[] Employees;  
}  

 

如果對該類進行編譯,並且使用 XML 架構定義工具生成其架構,可能會找到下面描述 Group 的 XML。

<xs:element name="NewGroupName" type="NewTypeName">

相比之下,如果是對該類的實例進行序列化,則只能在 XML 文檔中找到 NewGroupName。

<NewGroupName> . . .</NewGroupName>

 

 

最后來貼一個自己的XML解析實例

XML結構如下:

[html] view plain copy
<?xml version="1.0" encoding="utf-8"?>  
<Root>  
    <Person IDCard="610424199902230099" Name="小田雨" MedicalID="體檢編號" Sex="男" Age="22" MedicalRecordDate ="2011-01-01"  MedicalReportDate="2011-01-01"  
  MedicalCount="體檢次數"  HospitalID="001" HospitalName="興隆園醫院" >  
        <Results>  
            <Result></Result>  
            <Result></Result>  
            <Result></Result>  
        </Results>  
        <Conclusions>  
            <Conclusion></Conclusion>  
            <Conclusion></Conclusion>  
            <Conclusion></Conclusion>  
        </Conclusions>  
        <Suggestions>  
            <Suggestion></Suggestion>  
            <Suggestion></Suggestion>  
            <Suggestion></Suggestion>  
        </Suggestions>  
        <Health> 為空(預留)</Health>  
    </Person>  
  
    <MedicalItems>  
        <MedicalSub  ID ="0001" Name="化學檢查"  >  
            <MedicalType ID ="0001001" Name="血常規" MedicalDoc="體檢醫師名字" MedicalDate="2011-02-13">  
  
                <Item ID="000100010001" Name="白細胞" Unit="G/L" Parameters="3.7--10.0" >  
                    <Results>H==高,L=低,N=正常</Results>  
                    <Value>11.1</Value>  
                    <Disease></Disease>  
                    <MedicalBodyPart> </MedicalBodyPart>  
                    <MedicalImage> </MedicalImage>  
                    <Conclusion ></Conclusion>  
                </Item>  
                <Item ID="000100010002" Name="紅細胞" Unit="G/L" Parameters="3.7--10.0">  
                    <Results>H==高,L=低,N=正常</Results>  
                    <Value>11.1</Value>  
                    <Disease></Disease>  
                    <MedicalBodyPart> </MedicalBodyPart>  
                    <MedicalImage> </MedicalImage>  
                    <Conclusion ></Conclusion>  
                </Item>  
            </MedicalType>  
        </MedicalSub>  
        <MedicalSub  ID ="0002" Name="物理檢查"  >  
            <MedicalType ID ="0002001" Name="B超" MedicalDoc="體檢醫師名字" MedicalDate="2011-02-13">  
                <Item ID="000200010001" Name="胸部B超" Unit=" " Parameters="">  
                    <Results>A=異常,N=正常</Results>  
                    <Value></Value>  
                    <Disease>病種,未見異常</Disease>  
                    <MedicalBodyPart>檢查部位:胸部</MedicalBodyPart>  
                    <MedicalImage>影像所見</MedicalImage>  
                    <Conclusion >檢查結論</Conclusion>  
                </Item>  
                <Item ID="000200010002" Name="腹部B超" Unit=" " Parameters="">  
                    <Results>A=異常,N=正常</Results>  
                    <Value></Value>  
                    <Disease>病種,未見異常</Disease>  
                    <MedicalBodyPart>檢查部位:腹部</MedicalBodyPart>  
                    <MedicalImage>影像所見</MedicalImage>  
                    <Conclusion >檢查結論</Conclusion>  
                </Item>  
            </MedicalType>  
  
        </MedicalSub>  
        <MedicalSub  ID ="0005" Name="五官科"  >  
            <MedicalType ID ="0005001" Name="眼科" MedicalDoc="體檢醫師名字" MedicalDate="2011-02-13">  
                <Item ID="000500010001" Name="視力/右" Unit=" " Parameters="1.0-1.5">  
                    <Results>A=異常,N=正常</Results>  
                    <Value>1.5</Value>  
                    <Disease>病種,未見異常</Disease>  
                    <MedicalBodyPart>檢查部位</MedicalBodyPart>  
                    <MedicalImage>影像所見</MedicalImage>  
                    <Conclusion >檢查結論</Conclusion>  
                </Item>  
                <Item ID="000500010002" Name="矯正視力/右" Unit=" " Parameters="1.0-1.5">  
                    <Results>A=異常,N=正常</Results>  
                    <Value>0.8</Value>  
                    <Disease>病種,未見異常</Disease>  
                    <MedicalBodyPart>檢查部位</MedicalBodyPart>  
                    <MedicalImage>影像所見</MedicalImage>  
                    <Conclusion >檢查結論</Conclusion>  
                </Item>  
            </MedicalType>  
  
        </MedicalSub>  
    </MedicalItems>  
</Root>  

 

 

實例

C#代碼如下:

代碼有點多

[csharp] view plain copy
using System;  
using System.Collections.Generic;  
using System.Linq;  
using System.Text;  
using System.Xml;  
using System.Xml.Serialization;  
  
using System.IO;  
  
namespace 天健接口  
{  
    class Program  
    {  
        static void Main(string[] args)  
        {  
            Root r = new Root();  
  
            r.Person = new Person();  
            r.Person.IDCard = "22";  
            r.Person.Results = new List<string>();  
            r.Person.Results.Add("1");  
            r.Person.Results.Add("1");  
            r.Person.Results.Add("1");  
            r.Person.Suggestions = new List<string>();  
            r.Person.Suggestions.Add("2");  
            r.Person.Suggestions.Add("2");  
            r.Person.Suggestions.Add("2");  
  
            r.MedicalItems = new List<MedicalSub>();  
            MedicalSub ms = new MedicalSub();  
            ms.ID = "ss";  
            ms.Name="de";  
            ms.MedicalType = new MedicalType();  
            ms.MedicalType.ID = "wa";  
            ms.MedicalType.Name = "s";  
            ms.MedicalType.MedicalDoc= "qa";  
            ms.MedicalType.MedicalDate = "2010-5-5";  
            ms.MedicalType.Item = new List<Item>();  
            Item it = new Item();  
            it.ID = "f";  
            it.Name = "s";  
            it.Results = "s";  
            ms.MedicalType.Item.Add(it);  
            ms.MedicalType.Item.Add(it);  
            r.MedicalItems.Add(ms);  
            r.MedicalItems.Add(ms);  
  
            Console.WriteLine("序列化成功……");  
            Console.WriteLine(XmlSerialize.SerializeXML<Root>(r));  
              
             
  
        }  
    }  
  
    [Serializable]  
    public class Root  
    {  
        //[XmlElement]  
        public Person Person;  
  
        public List<MedicalSub> MedicalItems;  
    }  
  
    [Serializable]  
    public class Person  
    {  
        [XmlAttribute]  
        public string IDCard;  
  
        [XmlAttribute]  
        public string Name;  
  
        [XmlAttribute]  
        public string MedicalID;  
  
        [XmlAttribute]  
        public string Sex;  
  
        [XmlAttribute]  
        public string Age;  
  
        [XmlAttribute]  
        public string MedicalRecordDate;  
  
        [XmlAttribute]  
        public string MedicalReportDate;  
  
        [XmlAttribute]  
        public string MedicalCount;  
  
        [XmlAttribute]  
        public string HospitalID;  
  
        [XmlAttribute]  
        public string HospitalName;  
  
        [XmlArrayItem("Result")]  
        public List<string> Results;  
  
        [XmlArrayItem("Conclusion")]  
        public List<string> Conclusions;  
  
        [XmlArrayItem("Suggestion")]  
        public List<string> Suggestions;  
  
        public String Health;  
    }  
  
    [Serializable]  
    public class MedicalSub  
    {  
        [XmlAttribute]  
        public string ID;  
  
        [XmlAttribute]  
        public string Name;  
  
        public MedicalType MedicalType;  
  
    }  
  
    [Serializable]  
    public class MedicalType  
    {  
        [XmlAttribute]  
        public string ID;  
  
        [XmlAttribute]  
        public string Name;  
  
        [XmlAttribute]  
        public string MedicalDoc;  
  
        [XmlAttribute]  
        public string MedicalDate;  
  
        [XmlElement]  
        public List<Item> Item;  
    }  
  
    public class Item  
    {  
        [XmlAttribute]  
        public string ID;  
  
        [XmlAttribute]  
        public string Name;  
  
        [XmlAttribute]  
        public string Unit;  
  
        [XmlAttribute]  
        public string Parameters;  
  
  
        public string Results;  
  
        public string Value;  
  
        public string Disease;  
  
        public string MedicalBodyPart;  
  
        public string MedicalImage;  
  
        public string Conclusion;  
  
  
    }  
  
  
  
  
  
  
    public class XmlSerialize  
    {  
        /// <summary>  
        /// 反序列化XML為類實例  
        /// </summary>  
        /// <typeparam name="T"></typeparam>  
        /// <param name="xmlObj"></param>  
        /// <returns></returns>  
        public static T DeserializeXML<T>(string xmlObj)  
        {  
            XmlSerializer serializer = new XmlSerializer(typeof(T));  
            using (StringReader reader = new StringReader(xmlObj))  
            {  
                return (T)serializer.Deserialize(reader);  
            }  
        }  
  
        /// <summary>  
        /// 序列化類實例為XML  
        /// </summary>  
        /// <typeparam name="T"></typeparam>  
        /// <param name="obj"></param>  
        /// <returns></returns>  
        public static string SerializeXML<T>(T obj)  
        {  
            using (StringWriter writer = new StringWriter())  
            {  
                new XmlSerializer(obj.GetType()).Serialize((TextWriter)writer, obj);  
                return writer.ToString();  
            }  
        }  
    }  
  
  
}  

參考:

http://blog.csdn.net/bdstjk/article/details/7210742


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM