选择包含特定属性的所有xml节点

时间:2013-04-11 09:52:57

标签: c# xml xpath

我必须选择包含具有特定名称的属性的所有节点。

这是我目前的工作方法。

public List<string> RetrieveValuesForAttribute(string attributeName)
{
    var list = new List<string>();

    string xpath = "//*[@Name='" + attributeName + "']";
    XmlNodeList xmlNodeList = document.SelectNodes(xpath);

    foreach (XmlNode xmlNode in xmlNodeList)
    {
        list.Add(xmlNode.Attributes[attributeName].InnerText);
    }

    return list;
} 

我尝试选择包含具有方法参数attributeName中指定名称的属性的所有节点,并将值添加到变量list

示例:

此方法调用:

List<string> result = RetrieveValuesForAttribute("itemSelectedHandler");

应返回包含字符串“OnSelectedRelatedContactChanged”

的列表

这是xml文件:

<GroupBoxWrapper id="gbRelatedContacts" text="Related Contacts">
  <TabIndex>0</TabIndex>
  <TabStop>false</TabStop>
  <PanelWrapper id="pnlRelatedContactsView" width="1350">
    <TabIndex>0</TabIndex>
    <TabStop>false</TabStop>
    <ListViewWrapper id="lvRelatedContacts" itemSelectedHandler="OnSelectedRelatedContactChanged" itemDoubleClickHandler="OnRelatedContactDoubleClick">
      <TabIndex>0</TabIndex>
      <TabStop>true</TabStop>
      <ListViewColumns>
        <Column title="Name" mapNode="Contact\Name" />
        <Column title="Lastname" mapNode="Contact\Lastname" />
      </ListViewColumns>
    </ListViewWrapper>
  </PanelWrapper>
</GroupBoxWrapper>

进一步的问题: 使用LINQ解决这个问题会更好吗?

解决方案1:谢谢你,ywm

public List<string> RetrieveValuesForAttribute(string attributeName)
{
    var list = new List<string>();

    string xpath = @"//*[@" + attributeName + "]";
    XmlNodeList xmlNodeList = document.SelectNodes(xpath);

    foreach (XmlNode xmlNode in xmlNodeList)
    {
        list.Add(xmlNode.Attributes[attributeName].InnerText);
    }

    return list;
}

解决方案2:谢谢你,Jon Skeet

public List<string> RetrieveValuesForAttribute(string attributeName)
{
    //document is an XDocument
    return document.Descendants()
                   .Attributes(attributeName)
                   .Select(x => x.Value)
                   .ToList();
}

LINQ to XML解决方案对我来说更加优雅。

3 个答案:

答案 0 :(得分:9)

如果您可以使用LINQ to XML,那将完全无关紧要:

// Note that there's an implicit conversion from string to XName,
// but this would let you specify a namespaced version if you want.
public List<string> RetrieveValuesForAttribute(XName attributeName)
{
    // Assume document is an XDocument
    return document.Descendants()
                   .Attributes(attributeName)
                   .Select(x => x.Value)
                   .ToList();
} 

答案 1 :(得分:4)

您正在寻找的XPath应该是

"//*[@" + attributeName + "]"

您的原始XPath正在寻找具有值为Name的{​​{1}}属性的所有元素

这将查找具有attributeName

属性的任何元素
attributeName

将返回列元素

答案 2 :(得分:1)

我不确定C#语法,但我认为xpath值是错误的。 请尝试:“// * [@ itemSelectedHandler]”。 应该在c#

中做些什么
  string xpath = "//*[@" + attributeName + "]";