LINQ在查找XML节点时返回null。

4
我尝试使用XDocument类解析XML文件,并根据给定的条件选择父节点,如果其子节点与指定的字符串匹配。请见以下内容:

<SalesQuotes xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://api.some.com/version/1">
  <Pagination>
    <NumberOfItems>2380</NumberOfItems>
    <PageSize>200</PageSize>
    <PageNumber>1</PageNumber>
    <NumberOfPages>12</NumberOfPages>
  </Pagination>
  <SalesQuote>
    <Guid>825634b9-28f5-4aa7-98e7-5e4a4ed6bc6a</Guid>
    <LastModifiedOn>2018-01-09T12:23:56.6133445</LastModifiedOn>
    <Comments>Please note:
installation is not included in this quote
    </Comments>
  </SalesQuote>
</SalesQuotes>

我尝试使用:

var contents = File.ReadAllText(path: "test1.xml");
var doc = XDocument.Parse(contents);
var root = doc.Root;
var sq = root.Elements("SalesQuote");//return null

var theQuote = root.Elements("SalesQuote").Where(el => el.Element("Guid").Value == "825634b9-28f5-4aa7-98e7-5e4a4ed6bc6a");//return null

var theAlternativeQuote =
            from el in doc.Descendants("SalesQuote").Elements("Guid")
            where el.Value == "825634b9-28f5-4aa7-98e7-5e4a4ed6bc6a"
            select el;//return null

我似乎找不出问题所在。

非常感谢任何帮助!谢谢。

3个回答

6

你忽略了命名空间。

在你的XML中删除xmlns属性或尝试以下方法:

var contents = File.ReadAllText("XMLFile1.xml");
var doc = XDocument.Parse(contents);
var root = doc.Root;
XNamespace ns = "http://api.some.com/version/1";
var sq = root.Descendants(ns + "SalesQuotes"); //return null

var theQuote = root.Elements(ns + "SalesQuote")
    .Where(el => el.Element(ns + "Guid").Value == "825634b9-28f5-4aa7-98e7-5e4a4ed6bc6a"); //return null

var theAlternativeQuote =
    from el in doc.Descendants(ns + "SalesQuote").Elements(ns + "Guid")
    where el.Value == "825634b9-28f5-4aa7-98e7-5e4a4ed6bc6a"
    select el; //return null

1

是的,你缺少了可以通过document.Root.GetDefaultNamespace()获取的命名空间。

    // Load
    var document = XDocument.Parse(xml);
    var xmlns = document.Root.GetDefaultNamespace();

    // Find
    var query = from element in document
                    .Descendants(xmlns + "SalesQuote")
                    .Elements(xmlns + "Guid")
                where element.Value == "825634b9-28f5-4aa7-98e7-5e4a4ed6bc6a"
                select element;

请查看以下链接获取 LinqPad 示例:https://gist.github.com/dandohotaru/bc3766f98a81b3538a021dc573649cf3 - Dan Dohotaru

1

如果您不太关心保留当前的实现,可以考虑使用类型化的数据集并将XML加载到完全类型化的结构化对象中。

使用Linq查询这些对象将比您当前的实现更加直观。

您可能还会发现这个链接有用: SO问题:将XML文档反序列化为对象


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接