[英]Parsing an XML file -options?
我正在开发一个系统,以通过Exchange Web Services从电子邮件中提取XML附件,并通过我创建的自定义DAL对象将其输入数据库。
我已经设法提取XML附件并将其作为流准备好了……他们质疑如何解析此流并填充DAL对象。
我可以创建一个XMLTextReader并遍历每个元素。 除了我怀疑这是一种更加流畅的方式之外,我没有看到其他任何问题。 读者似乎将开始标签,标签内容和结束标签视为不同的元素(使用reader.NodeType)。 我希望myValue被认为是一个元素,而不是三个。 就像我说的,我可以解决这个问题,但是我敢肯定必须有更好的方法。
我遇到了使用XML序列化器(对我来说是全新的想法)的想法,但是快速浏览后发现它们不能处理ArrayLists和List(我正在使用List)。
再说一次,我是LINQ的新手,但也提到了LINQ-to-XML,但是我看到的例子似乎相当复杂-尽管我只是不熟悉。
基本上,我不需要笨拙的系统,但是我不想因为学习曲线太复杂而使用任何复杂的技术。
将这个XML / Stream转换成我的DAL对象的最简单,最有效的方法是什么?
XML示例:
<?xml version="1.0" encoding="UTF-8"?>
<enquiry>
<enquiryno>100001</enquiryno>
<companyname>myco</companyname>
<typeofbusiness>dunno</typeofbusiness>
<companyregno>ABC123</companyregno>
<postcode>12345</postcode>
<contactemail>me@example.com</contactemail>
<firstname>My</firstname>
<lastname>Name</lastname>
<vehicles>
<vehicle>
<vehiclereg>54321</vehiclereg>
<vehicletype>Car</vehicletype>
<vehiclemake>Ford</vehiclemake>
<cabtype>n/a</cabtype>
<powerbhp>130</powerbhp>
<registrationdate>01/01/2003</registrationdate>
</vehicle>
</vehicles>
</enquiry>
更新1 :基于Graham的示例,我正在尝试反序列化。 我想我已经设置了DAL进行序列化,包括为每个属性指定[XmlElement("whatever")]
。 并且我尝试使用以下方法反序列化:
SalesEnquiry enquiry = null;
XmlSerializer serializer = new XmlSerializer(typeof(SalesEnquiry));
enquiry = (SalesEnquiry)serializer.Deserialize(stream);
但是,我得到一个例外:“ There is an error in XML document (2, 2)
”。 内部异常状态{"<enquiry xmlns=''> was not expected."}
结论 (更新):
我以前的问题是XML文件中的元素(Enquiry)!=类的名称(SalesEnquiry)。 而不是该类的[XmlElement]
属性,我们需要一个[XmlRoot]
属性。 为了完整起见,如果希望在序列化过程中忽略类中的属性,请使用[XmlIgnore]
属性。
我已经成功地序列化了我的对象,现在已经成功获取了传入的XML并将其反序列化为SalesEnquiry对象。
这种方法比手动解析XML容易得多。 好的,学习曲线很陡,但这是值得的。
谢谢!
如果您的XML使用模式(即,您总是要知道哪些元素出现以及它们在树中的位置),则可以使用XmlSerializer
创建对象。 您只需要在类上具有一些属性即可告诉序列化程序它们对应的XML元素或属性。 然后,您只需加载XML,使用您要创建的.NET对象的类型创建一个新的XmlSerializer
,然后调用Deserialize
方法。
例如,您有一个类似的类:
[Serializable]
public class Person
{
[XmlElement("PersonName")]
public string Name { get; set; }
[XmlElement("PersonAge")]
public int Age { get; set; }
[XmlArrayItem("Child")]
public List<string> Children { get; set; }
}
然后输入这样的XML(在此示例中保存在文件中):
<?xml version="1.0"?>
<Person>
<PersonName>Bob</PersonName>
<PersonAge>35</PersonAge>
<Children>
<Child>Chris</Child>
<Child>Alice</Child>
</Children>
</Person>
然后您创建一个Person
实例,如下所示:
Person person = null;
XmlSerializer serializer = new XmlSerializer(typeof(Person));
using (FileStream fs = new FileStream(GetFileName(), FileMode.Open))
{
person = (Person)serializer.Deserialize(fs);
}
更新:根据您的上一次更新,我想您可能需要在充当根元素的类上指定XmlRoot
属性(即SalesEnquiry
),否则XmlSerializer
可能有点困惑,因为您引用的是空名称空间在您的XML中( xmlns=''
似乎不正确)。
XmlSerializer确实支持数组和列表...,只要所包含的类型可序列化即可。
我发现Xsd2Code对于这种事情非常有帮助: http : //xsd2code.codeplex.com/
基本上,您所需要做的就是编写一个xsd文件(一个XML模式文件)并指定一些命令行开关。 Xsd2Code将自动生成一个C#类文件,其中包含所有类和属性以及处理序列化所需的一切。 这不是一个完美的解决方案,因为它不支持XSD的所有方面,但是如果您的XML文件是相对简单的元素和属性集合,那么它对您来说应该是一个不错的捷径。
在Codeplex上还有另一个类似的项目,称为Linq to XSD( http://linqtoxsd.codeplex.com/ ),该项目旨在实施整个XSD规范,但是上一次我检查时,该项目不再受支持并且还没有真正准备好黄金时间。 认为值得一提。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.