C#将不同类型的xml数组反序列化为多个数组
Posted
技术标签:
【中文标题】C#将不同类型的xml数组反序列化为多个数组【英文标题】:C# deserialize xml array of different types into multiple arrays 【发布时间】:2016-05-05 02:22:00 【问题描述】:我有以下 xml:
<Applications>
<AccessibleApplication></AccessibleApplication>
<AccessibleApplication></AccessibleApplication>
<EligibleApplication></EligibleApplication>
<EligibleApplication></EligibleApplication>
</Applications>
有没有办法将其反序列化为 C# 对象,以便 AccessibleApplications 和 EligibleApplications 是两个独立的数组?我尝试了以下方法,但出现异常,因为“应用程序”被多次使用。
[XmlArray("Applications")]
[XmlArrayItem("AccessibleApplication")]
public List<Application> AccessibleApplications get; set;
[XmlArray("Applications")]
[XmlArrayItem("EligibleApplication")]
public List<Application> EligibleApplications get; set;
例外情况是: 命名空间“”中的 XML 元素“应用程序”已存在于当前范围内。使用 XML 属性为元素指定另一个 XML 名称或命名空间。
这可能吗?
谢谢!
编辑:我忘了说我不想仅仅为了为两个数组提供一个容器对象而有一个“应用程序”类。我有几种这样的情况,我不希望这些类杂乱无章,其唯一目的是拆分两个相同类型的数组。
我希望能够使用诸如 [XmlArrayItem="Application/AccessibleApplication"] 之类的某种标签将两个数组反序列化为外部对象,而无需创建“应用程序”类。
【问题讨论】:
【参考方案1】:我找到了一个相当巧妙的方法,首先创建一个这样的类:
using System.Xml.Serialization;
[XmlRoot]
public class Applications
[XmlElement]
public string[] AccessibleApplication;
[XmlElement]
public string[] EligibleApplication;
请注意元素如何成为单独的数组。现在使用这个类(我的 XML 在一个单独的文件中,因此是 XmlDocument 类)。
var doc = new XmlDocument();
doc.Load("../../Apps.xml");
var serializer = new XmlSerializer(typeof(Applications));
Applications result;
using (TextReader reader = new StringReader(doc.InnerXml))
result = (Applications)serializer.Deserialize(reader);
现在为了证明这是可行的,您可以将其全部写入控制台应用程序并执行 foreach 以打印数组中的所有值,如下所示:
foreach (var app in result.AccessibleApplication)
Console.WriteLine(app);
foreach (var app in result.EligibleApplication)
Console.WriteLine(app);
【讨论】:
【参考方案2】:您可以使用 XmlElement 属性来反序列化到不同的列表:
public class Applications
[XmlElement("AccessibleApplication")]
public List<Application> AccessibleApplications get; set;
[XmlElement("EligibleApplication")]
public List<Application> EligibleApplications get; set;
public class Application
[XmlText]
public string Value get; set;
所以对于一个示例 XML:
<Applications>
<AccessibleApplication>xyz</AccessibleApplication>
<AccessibleApplication>abc</AccessibleApplication>
<EligibleApplication>def</EligibleApplication>
<EligibleApplication>zzz</EligibleApplication>
</Applications>
以下 sn-p 将输出以下内容:
using (var reader = new StreamReader("XMLFile1.xml"))
var serializer = new XmlSerializer(typeof(Applications));
var applications = (Applications)serializer.Deserialize(reader);
Console.WriteLine("AccessibleApplications:");
foreach (var app in applications.AccessibleApplications)
Console.WriteLine(app.Value);
Console.WriteLine();
Console.WriteLine("EligibleApplications:");
foreach (var app in applications.EligibleApplications)
Console.WriteLine(app.Value);
输出:
可访问的应用程序:
xyz
abc
符合条件的申请:
定义
zzz
【讨论】:
【参考方案3】:你可以使用这个类从字符串创建对象,从对象创建字符串和从对象创建字节[]
StringToObject
var applicationObject = new XmlSerializerHelper<Applications>().StringToObject(xmlString);
ObjectToString
var xmlString = new XmlSerializerHelper<Applications>().ObjectToString(applicationObject);
ObjectToByteArray
var byteArray = new XmlSerializerHelper<Applications>().ObjectToByteArray(applicationObject);
XmlSerializerHelper:
namespace ***
public class XmlSerializerHelper<T> where T : class
private readonly XmlSerializer _serializer;
public XmlSerializerHelper()
_serializer = new XmlSerializer(typeof(T));
public T ToObject(string xml)
return (T)_serializer.Deserialize(new StringReader(xml));
public string ToString(T obj, string encoding)
using (var memoryStream = new MemoryStream())
_serializer.Serialize(memoryStream, obj);
return Encoding.GetEncoding(encoding).GetString(memoryStream.ToArray());
public byte[] ToByteArray(T obj, Encoding encoding = null)
var settings = GetSettings(encoding);
using (var memoryStream = new MemoryStream())
using (var writer = XmlWriter.Create(memoryStream, settings))
_serializer.Serialize(writer, obj);
return memoryStream.ToArray();
private XmlWriterSettings GetSettings(Encoding encoding)
return new XmlWriterSettings
Encoding = encoding ?? Encoding.GetEncoding("ISO-8859-1"),
Indent = true,
IndentChars = "\t",
NewLineChars = Environment.NewLine,
ConformanceLevel = ConformanceLevel.Document
;
你的班级:
[XmlRoot]
public class Applications
[XmlElement("AccessibleApplication")]
public string[] AccessibleApplication get; set;
[XmlElement("EligibleApplication")]
public string[] EligibleApplication get; set;
或者
[XmlRoot]
public class Applications
[XmlElement("AccessibleApplication")]
public List<string> AccessibleApplication get; set;
[XmlElement("EligibleApplication")]
public List<string> EligibleApplication get; set;
干杯。
【讨论】:
以上是关于C#将不同类型的xml数组反序列化为多个数组的主要内容,如果未能解决你的问题,请参考以下文章
C# XMLSerializer 将错误的类型反序列化为 List
将位置坐标的 Mongo BSON 数组反序列化为自定义 C# 类