Ivan-Mark Debono
Ivan-Mark Debono

Reputation: 16280

C# XML get nodes based on attribute

I have the following xml:

<root ...>
  <Tables>
    <Table content="..">
    </Table>
    <Table content="interesting">
      <Item ...></Item>
      <Item ...></Item>
      <Item ...></Item>
    </Table>
    ...etc...
  </Tables>
</root>

I'm using the following code to get the items from the 'interesting' node:

XElement xel = XElement.Parse(resp);

var nodes = from n in xel.Elements("Tables").Elements("Table")
            where n.Attribute("content").Value == "interesting"
            select n;

var items = from i in nodes.Elements()
            select i;

Is there a simpler, cleaner way to achieve this?

Upvotes: 1

Views: 3962

Answers (4)

Deepak Saralaya
Deepak Saralaya

Reputation: 457

using xml document
XmlDocument xdoc = new XmlDocument();

var item= xdoc.GetElementsByTagName("Table[@content='interesting']/Item");

Upvotes: 1

Sergey Berezovskiy
Sergey Berezovskiy

Reputation: 236188

You can use XPath (extension is in System.Xml.XPath namespace) to select all items in one line:

var items = xel.XPathSelectElements("//Table[@content='interesting']/Item");

Upvotes: 2

p.s.w.g
p.s.w.g

Reputation: 148980

If you don't need nodes outside of your query for items, you can just do this:

var items = from n in xel.Elements("Tables").Elements("Table")
            where n.Attribute("content").Value == "interesting"
            from i in n.Elements()
            select i;

Upvotes: 1

Jon Skeet
Jon Skeet

Reputation: 1499790

Well there's no point in using a query expression for items, and you can wrap the whole thing up very easily in a single statement. I wouldn't even bother with a query expression for that:

var items = XElement.Parse(resp)
                    .Elements("Tables")
                    .Elements("Table")
                    .Where(n => n.Attribute("content").Value == "interesting")
                    .Elements();

Note that this (and your current query) will throw an exception for any Table element without a content attribute. If you'd rather just skip it, you can use:

.Where(n => (string) n.Attribute("content") == "interesting")

instead.

Upvotes: 5

Related Questions