Monday, February 21, 2011

Working with XML in C# .NET 3.5 Using XElement, xmlTrees and LINQ to XML

XElement
The XElement class represents an XML element. All elements in XML have names, they may or may not have attributes or content.

The namespace System.Xml.Linq is required when working with XElement.

The following link provides information on the different types of content an XElement can contain.

http://msdn.microsoft.com/en-us/library/bb943882(v=VS.90).aspx

For more information on the XElement class from the Microsoft site see the following link.

http://msdn.microsoft.com/en-us/library/system.xml.linq.xelement(v=VS.90).aspx

The following link provides details on members the XElement type exposes.

http://msdn.microsoft.com/en-us/library/system.xml.linq.xelement_members(v=VS.90).aspx

To create a single XML element with no content:

XElement objXElement = new XElement("Element1");

objXElement now contains the following XML:

<Element1 />


To add content to the element:

XElement obXjElement = new XElement("Element1", "ABCD");

objXElement now contains the following XML:

<Element1>ABCD</Element1>



To create a parent element with a descendant, add a new XElement object as the content argument:

XElement objXElement = new XElement("Parent", new XElement( "ChildElement1","ABCD");

objXElement now contains the following XML:

<Parent> 

     <ChildElement1>ABCD</ChildElement1> 

</Parent>


The XML produced matches the standard XML format.

As more XElements objects are added as content arguments an xmlTree can be created.

In addition to the XElement class, there is also a XDocument class which can be used to create XML documents. The following link provides information on this class from the Microsoft site.

http://msdn.microsoft.com/en-us/library/system.xml.linq.xdocument(v=VS.90).aspx

Working with XElement is far simpler than working with XDocument objects.
 
xmlTree
 
The following code snippet creates an xmlTree.


XElement xmlTreeExample =

   new XElement(“Parents”,

           new XElement("Parent",

                   new XElement( "ChildElement1","ABCD"),

                   new XElement(“ChildElement2”,

                           new XElement(“GrandChildElement1”, “1234”)

                    )
             )
    );

xmlTreeExample now contains the following XML:

<Parents>

    <Parent>

        <ChildElement1>ABCD</ChildElement1>

        <ChildElement2>

            <GrandChildElement1>1234</GrandChildElement1>

        </ChildElement2>

    </Parent>

</Parents>


Creating an xmlTree using XElement.Parse

The above example is not the only way to create an xmlTree, XElement’s Parse method can be used to create an xmlTree from a string containing XML.

XElement xmlTreeExample2 =

   new XElement.Parse(xmlString, LoadOptions.None);

LoadOptions set to None will not preserve white spaces or retain line information. If this is required then set LoadOptions to LoadOptions.PreserveWhitespace or LoadOptions.SetLineInfo. Please note, using LoadOptions.SetLineInfo will mean taking a performance hit.

Creating an xmlTree using XElement.Load

Using the code snippet above, the XElement object ‘xmlTreeExample2’ can be saved in an XML file.

xmlTreeExample2.Save(“TestTree.xml”);

The Load method allows an XElement to be loaded from an XML file.

XElement xmlTreeExample3 = XElement.Load(“TestTree.xml”);

The Load method can also be used to load an XElement from a TextReader, xmlReader and using a stream an XElement instance can be created. See the following link for more information on these alternative methods.

http://msdn.microsoft.com/en-us/library/bb350413.aspx

The following link provides more information on creating xmlTrees

http://msdn.microsoft.com/en-us/library/bb387068(v=VS.90).aspx
 
LINQ to XML
 
LINQ to XML is an approach to programming XML in .NET using LINQ query expressions. Query results can be used as parameters in XElement and XAttribute objects when creating xmlTrees. This functionality(known as functional construction) allows xmlTrees to be transformed from one shape to another.
 
Simple LINQ to XML queries
 
XElement xmlTreeExample4 contains the following XML:

<Parents>

     <Parent>

        <ChildElement1>ABCD</ChildElement1>

        <ChildElement2>

            <GrandChildElement1>1234</GrandChildElement1>

        </ChildElement2>

    </Parent>

    <Parent>

         <ChildElement1>EFGH</ChildElement1>

         <ChildElement2>

             <GrandChildElement1>5678</GrandChildElement1>

         </ChildElement2>

    </ Parent>

</Parents>


The following code snippet shows how to retrieve the value of the element ChildElement1 from each parent element in xmlTreeExample4.

IEnumerable elementValue =

             from parent in xmlTreeExample4.Descendants(“Parent”)

             select (string) parent.Element(“ChildElement1”);
 
The following code snippet shows how to retrieve the value of the element GrandChildElement1 from each parent element in the xmlTreeExample4.

IEnumerable elementValue =

             from parent in xmlTreeExample4.Descendants(“Parent”)

             select (int) parent.Element(“ChildElement2”).Element(“GrandChildElement1”);
 
To retrieve the values of all descendants of each Parent element the following code shows how this can be achieved.

var parentData = from parent in xmlTreeExample4.Descendants(“Parent”)

select new

{

            child = parent.Element(“ChildElement1”).Value,

            grandchild = parent.Element(“ChildElement2”).Element(“GrandChildElement1”).Value

};

A for each loop can be used to loop through each object in parentData, like so

foreach (var parent in parentData)

{
             //do some processing here
}

If each parent element in xmlTreeExample4 contained an attribute called ‘ParentName’, for example



<Parent ParentName=”FirstParent”>


To retrieve this ‘ParentName’ attribute value, the following can be done

IEnumerable attributeValue =

            from parent in xmlTreeExample4.Descendants(“Parent”)

            select (string) parent.Attribute("ParentName");
 
See the Microsoft site for more information on LINQ to XML

http://msdn.microsoft.com/en-us/library/bb387098(v=VS.90).aspx

For more information on Programming C# LINQ Query Expressions see this link

http://msdn.microsoft.com/en-us/library/bb397676(v=VS.90).aspx