Linq to xml如何在c#中按值获取XElement

时间:2017-01-15 23:13:30

标签: c# xml linq linq-to-xml

我有一个xml:

<?xml version="1.0" encoding="utf-8"?>
<Fields>
  <Field>
    <Name>DEMOFIELD</Name>
    <Category>HardwareSoftwareRequirement</Category>
  </Field>
</Fields>

当我这样做时:

XElement xDoc = XElement.Load("File.xml");                
var x= xDoc.Descendants("Field").Where(elem => elem.Value == "DEMOFIELD");//returns no element

这不会返回任何东西。但是,当我这样做时:

var x= xDoc.Descendants("Field").Where(elem => elem.Value.Contains( "DEMOFIELD"));//returns no element

在迭代时,而不是e.Value,它会返回:DEMOFIELDHardwareSoftwareRequirement,它不能只是DEMOFIELD吗?

然后迭代以获取值

foreach(XElement e in x)
{
    _log.Debug(e.Value);//no value here
}

2 个答案:

答案 0 :(得分:1)

您需要确保正在比较正确元素的值,使用嵌套XML很容易出错。在您的情况下,您正在比较Field元素的值(将是连接的所有内部值),但您的意思是将其与Name元素进行比较。

试试这个:

var xml = @"<?xml version=""1.0"" encoding=""utf-8""?>
<Fields>
  <Field>
    <Name>DEMOFIELD</Name>
    <Category>HardwareSoftwareRequirement</Category>
  </Field>
</Fields>";
var xdoc = XDocument.Load(new StringReader(xml));
var x = xdoc.Descendants("Field").Where(elem => elem.Element("Name")?.Value == "DEMOFIELD");

您现在仍然拥有Field元素,因此如果您想要获得类别所需的类别,那么您可以这样做:

x.First().Element("Category").Value

答案 1 :(得分:1)

帖子中的代码按值获取节点,但它不是您要查找的节点。

xDoc.Descendants("Field")选择名为“Field”的所有节点,但该节点只有子节点。因此,当您在该节点上调用.Value时,将通过连接所有子项的值来计算该值(“DEMOFIELD”+“HardwareSoftwareRequirement”=“DEMOFIELDHardwareSoftwareRequirement”)。

根据您实际查找的内容,您需要选择所有“名称”节点并按值过滤或检查名为“名称”的子节点的值:

  var nameByValue = xDoc.Descendants("Name")
        .Where(elem => elem.Value == "DEMOFIELD");
  var fieldByChildValue = xDoc.Descendants("Field")
        .Where(elem => elem.Element("Name").Value == "DEMOFIELD");