Dim xml = <Root>
<Parent id="1">
<Child>Thomas</Child>
</Parent>
<Parent id="2">
<Child>Tim</Child>
<Child>Jamie</Child>
</Parent>
</Root>
Dim parents = xml.Elements
In this case, children
includes all the Parent elements and all of the Child elements. What's the best way to grab only the direct descendants of <Root>
?
Should I write a LINQ query that selects elements where parent = <Root>
? Or is there some built-in method I'm missing that can get this for me?
EDIT: I had some confusion between XElement.Elements
and XElement.Descendants
. As Ruben Bartelink pointed out, XElement.Elements
will give me exactly what I was looking for.
The most important advantage of LINQ to XML is its integration with Language-Integrated Query (LINQ). This integration enables you to write queries on the in-memory XML document to retrieve collections of elements and attributes.
The XElement class is one of the fundamental classes in LINQ to XML. It represents an XML element. The following list shows what you can use this class for: Create elements. Change the content of the element.
XElement.Elements gets the collection of child elements. For example ...
var s = @"<root>
<e1>
<e2>
</e2>
</e1>
<e1>
<e2>
</e2>
</e1>
<e1>
<e2>
</e2>
</e1>
</root>";
var doc = XElement.Load( new StringReader(s) );
Console.WriteLine( doc.Elements().Count() ); // 3
Console.WriteLine( doc.Descendants().Count()); //6
Exec summary - you want:
xml.Elements.Select(function(element) new XElement(element.Name,element.Attributes))
First answer:
XElement.Descendants
, or is it a trick question ? :P There's an example of usage of Descendants here
Revised answer, thanks Tormod -- something did feel wrong!:
Elements gives direct descendants, as you're looking for. Descendants gives the full hierarchy [as you are alleging Elements does]. (The example I linked to makes this clear. Apologies for the confusion!
So, finally, what you're looking for is (this time in VB):
Dim xml = <Root>
<Parent id="1">
<Child>Thomas</Child>
</Parent>
<Parent id="2">
<Child>Tim</Child>
<Child>Jamie</Child>
</Parent>
</Root>
REM All nodes two levels down in the hierarchy
Dim level2Nodes = xml.Elements.SelectMany(function(element) element.Elements)
level2Nodes.Dump
REM All Child nodes, no matter where they are:
Dim children = xml.Descendants("Child")
Each of which will yield you the 3 ``` elements for different reasons as covered in the REMs.
(Paste the above directly into LINQPad in VB statement mode)
I now see what might be confusing you - when you use Elements and look at it in a visualiser, you are still seeing the children:-
Dim parents = xml.Elements
If you only want the actual names, you can use something like:
Dim parentNames = xml.Elements.Select(function(element) element.Name)
Note that in each of these cases, you are getting two results.
If you really want to strip out the chidren, you want:
Dim parentElements = xml.Elements.Select(function(element) new XElement(element.Name,element.Attributes))
Can you extend your question to show what you're really looking for?
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With