LINQ to XML - XPath

by Arnold Matusz 9 11 2008

LINQ to SQL may be dying these days, and to be frank that’s not a big deal as the Entity Framework is out which will 100% replace it. But LINQ as a concept is something new and won’t be out for some time!

While doing some configuration work I got into a sitation where I needed to query an XML file. Immediately my thoughts went to LINQ, and in term LINQ to XML. It is a great addition to the LINQ family but in terms of readability it’s far cry away from the old days when XPath was in use.

After a short search I noticed that the System.Xml.XPath namespace contains exactly what I need: LINQ to XML Extension methods. The 3 additional methods are: XPathEvaluate() which returns an object type, XPathSelectElement() which returns an XElement type and XPathSelectElemens() wich returns IEnumerable<XElement>.

Reading the documentation of this Extension class on MSDN lets us know the following: “There is some performance penalty for using these methods. Using LINQ to XML queries yields better performance.” So it is only advisable to use such LINQ to XML with XPath queries if and only if your application won’t suffer from the slight loss of performance!

The reason why I’m willing to allow such a performance loss in my application is the maintenability factor. Normally the maintenance cycle of an application is many times longer than the development cycle. This is why we always need to take care about how well our code is written! A clear query in a succinct syntax is ever easier to read, thus easier to maintain than a very long expression with many “calls” chained together

As a short demonstration of the idea please consider reading the following example:
Consider the following XML file!


<Clients>

   <Client>

     <CompanyName>Name 1</CompanyName>

         <ContactPerson>

             <FirstName>Firstname 1</FirstName>

             <LastName>Lastname 1</LastName>

             <Phone>Phone 1</Phone>

         </ContactPerson>

   </Client>

   <Client>

     <CompanyName>Name 2</CompanyName>

         <ContactPerson>

             <FirstName>Firstname 2</FirstName>

             <LastName>Lastname 2</LastName>

             <Phone>Phone 2</Phone>

         </ContactPerson>

   </Client>
</Clients>

In order to receive the phone number of the Contact Person whose FirstName is “FirstName 2” using LINQ to SQL you’ld need to use something similar to:

from xElem in xDoc.Descendants("Clients").Descendants("Client").Descendants("ContactPerson")
where xElem.Element("FirstName").Value == "Firstname 2"
select new { PhoneNumber = xElem.Element("Phone").Value };

But by using XPath we could simplify this allot. Only one line is sufficient to execute the query, and it is extremely clear which elements we parse and what we query for! Of course this sample will throw an exception if there is no contact person whose Firstname is “Firstname 2”. It will generate an InvalidOperationException due to the First() call with the following exception message: “Sequence contains no elements”. Please consider reading my post about this Exception if you are interested in how to avoid it!

xDoc.XPathSelectElements("//Clients/Client/ContactPerson[FirstName='Firstname 2']")
.First().Element("Phone").Value;

An extensive XPath Syntax reference can be found on www.w3schools.com. Once again, if performance is not an issue in your application consider using XPath as it’s much more “visible”, much more clear thus much easier to maintain than a regual LINQ to XML query.

LINQ to XML for XPath reference is also available on MSDN.

DZone it Digg it Submit to StumbleUpon Submit to Technorati Submit to reddit.com Submit to del.icio.us Submit to NewsVine Submit to Furl Submit to BlinkList

Tags: , , ,

C# | LINQ | Programming

Comments

11/10/2008 3:24:05 AM #

trackback

Trackback from DotNetKicks.com

LINQ to XML - XPath

DotNetKicks.com |

11/10/2008 8:14:13 AM #

Jarrett

A good idea for another blog post would be to actually measure the performance difference and graph it.

Nice post.

Jarrett |

11/10/2008 9:17:05 AM #

Arnold Matusz

Thanks for the idea Smile. The interesting thing is that I was allready planning on how to generate a complex xml file on which I would want to performance test a few queries using both LINQ to XML and LINQ to XML with XPath. I'm glad that you somebody else had a similar idea Smile.

Arnold Matusz Romania |

1/11/2009 8:39:45 AM #

trackback

Trackback from Web Development Community

LINQ to XML - XPath

Web Development Community |