Blog LogoBlog Logo

Navigating XML (LINQ to XML series - Part 3)

18 May 2008 ~ 2 min read


In my last two posts (part 1 and part 2) I’ve been introducing you to the the new XML classes in .NET 3.5. In this post I’ll continue that and show you some of the ways to navigate through XML. First of all, lets start with a simple hierarchy of XML elements:

XElement root = new XElement("FirstGeneration",
                    new XElement("SecondGeneration",
                        new XElement("ThirdGeneration",
                            new XElement("FourthGeneration"))));

Which looks like this when rendered as XML:

<FirstGeneration>
  <SecondGeneration>
    <ThirdGeneration>
      <FourthGeneration />
    </ThirdGeneration>
  </SecondGeneration>
</FirstGeneration>

Also in the last post I used Element to get a specific element from the current element. For example:

XElement child = root.Element("SecondGeneration");

Elements

If root (or FirstGeneration) only had one child element called “SecondGeneration” then everything is fine, you get what you asked for. However, if it contains multiple children all called “SecondGeneration” then you will only get the first element called “SecondGeneration”. For example, if you add the following to the code above:

root.Add(new XElement("SecondGeneration","2"));
root.Add(new XElement("SecondGeneration","3"));

You will get a piece of XML that looks like this:

<FirstGeneration>
  <SecondGeneration>
    <ThirdGeneration>
      <FourthGeneration />
    </ThirdGeneration>
  </SecondGeneration>
  <SecondGeneration>2</SecondGeneration>
  <SecondGeneration>3</SecondGeneration>
</FirstGeneration>

If you want to get all those additional children called “SecondGeneration” you will need to use the Elements (note the plural) method. For example:

IEnumerable<XElement> children = root.Elements("SecondGeneration");

You’ll also note that we don’t get a collection returned but an enumerable. This give us the opportunity to exploit many of the new extension methods. But I’ll leave them for another post. For the moment, we just need to know that it make it easy for us to enumerate over the data using a foreach loop. For example:

foreach (XElement child in children)
{
    Console.WriteLine(child);
    Console.WriteLine(new string('-', 50));
}

This will write out:

<SecondGeneration>
  <ThirdGeneration>
    <FourthGeneration />
  </ThirdGeneration>
</SecondGeneration>
--------------------------------------------------
<SecondGeneration>2</SecondGeneration>
--------------------------------------------------
<SecondGeneration>3</SecondGeneration>
--------------------------------------------------

Parent

Using the same root object as above, we can see how to navigate back up the XML tree using Parent.

XElement grandchild = root.Element("SecondGeneration").Element("ThirdGeneration");
Console.WriteLine(grandchild.Parent);

The result of the code will be that the SecondGeneration element is printed.


Headshot of Colin Mackay

Hi, I'm Colin. I'm a software engineer with over 30 years of experience based in central Scotland, specialising in Microsoft technologies, initially with C++ and then in C#. I was a Microsoft MVP from 2007 to 2010 and a Code Project MVP from 2005 to 2009.