Select XML Nodes with XPath in C#

To select XML nodes with XPath in C#, load the XML document, call Document.Evaluate() with a node-set expression and XPathResultType.Any, and retrieve matches with IXPathResult.IterateNext(). Pass a selected node as the context node when evaluating a relative XPath expression.

XPath (XML Path Language) is based on the DOM representation of a document. You can use XPath to find XML nodes that match criteria defined in an expression, including element names, predicates, axes, attribute selection, and relative paths.

This article shows C# examples for selecting required information from an XML file with XPath queries. For XPath over HTML documents, see Use XPath in HTML with C#.

XPath Queries to Select XML Nodes

These examples show how to select the required information from an XML file using XPath. The sample cars.xml contains car dealers, their names and phone numbers, and lists of their cars.

The following sections build XPath expressions progressively to select dealers, filter their cars, and extract specific values.

Select All Dealer Nodes in the XML File

XPath is used programmatically to evaluate expressions and pick specific nodes in an XML document. To select nodes from XML, use the Evaluate() method.

Start with the XPath expression //Dealer. It selects all Dealer elements in the document:

The same XPath expression can be evaluated in C# with Document.Evaluate():

1IXPathResult dealers = doc.Evaluate("//Dealer", doc, doc.CreateNSResolver(doc), XPathResultType.Any, null);

The result contains every Dealer element without additional filtering.

Filter Dealers by Car Model Year

Add a predicate to find dealers that have at least one descendant Car with a descendant Model value greater than 2005. The expression is //Dealer[descendant::Car[descendant::Model > 2005]].

XPath axes describe relationships between the context node and other nodes. The following axes are useful when querying the sample XML:

AxisRelationshipExampleContext in cars.xml
childDirect childrenchild::Car or CarCars
descendantChildren, grandchildren, and other descendantsdescendant::CarDealer
parentDirect parentparent::DealerName directly under Dealer
ancestorParent, grandparent, and other ancestorsancestor::DealersCar
following-siblingSiblings after the context nodefollowing-sibling::CarFirst Car in Cars
preceding-siblingSiblings before the context nodepreceding-sibling::CarSecond Car in Cars
attributeAttributes of the context elementattribute::CarID or @CarIDCar

The child axis is the default, so Car is equivalent to child::Car.

The same XPath expression can be evaluated in C# with Document.Evaluate():

1IXPathResult dealers = doc.Evaluate("//Dealer[descendant::Car[descendant::Model > 2005]]", doc, doc.CreateNSResolver(doc), XPathResultType.Any, null);

Filter Dealers by Car Model Year and Price

Next, add a price condition with and descendant::Price < 25000.

The XPath expression is //Dealer[descendant::Car[descendant::Model > 2005 and descendant::Price < 25000]]. Note: the conditions for price and year of manufacture are combined with and, which means that both conditions must be true at the same time:

The same XPath expression can be evaluated in C# with Document.Evaluate():

1IXPathResult dealers = doc.Evaluate("//Dealer[descendant::Car[descendant::Model > 2005 and descendant::Price < 25000]]", doc, doc.CreateNSResolver(doc), XPathResultType.Any, null);

The expression selects only dealers that have at least one Car whose descendant Model value is greater than 2005 and whose descendant Price value is less than 25,000.

Select XML Dealer Nodes with XPath in C#

The following C# example selects dealers that have a matching car and prints the TextContent of each selected Dealer node:

  1. Load an existing XML file ( cars.xml).
  2. Pass //Dealer[descendant::Car[descendant::Model > 2005 and descendant::Price < 25000]] to the Evaluate() method of the Document class.
  3. Retrieve each matched node with IXPathResult.IterateNext().
  4. Print the TextContent of each selected Dealer node to the console.
 1// Use XPath to select nodes from XML
 2
 3// Create an instance of a document
 4using (HTMLDocument doc = new HTMLDocument(Path.Combine(DataDir, "cars.xml")))
 5{
 6    // Select dealers that match XPath expression
 7    IXPathResult dealers = doc.Evaluate("//Dealer[descendant::Car[descendant::Model > 2005 and descendant::Price < 25000]]", doc, doc.CreateNSResolver(doc), XPathResultType.Any, null);
 8    Node dealer;
 9
10    // Iterate over the selected dealers
11    while ((dealer = dealers.IterateNext()) != null)
12    {
13        Console.WriteLine(dealer.TextContent);
14    }
15}

Extract Values from Selected XML Nodes in C#

The previous example prints the complete TextContent of every Dealer node matched by //Dealer[descendant::Car[descendant::Model > 2005 and descendant::Price < 25000]]. You can instead evaluate relative XPath expressions inside the loop to extract only the required values.

The expression concat('Dealer name: ', Name/text(), ' Telephone: ', Telephone/text()) combines the direct Name and Telephone child values of the current Dealer. Pass the current dealer as the contextNode, request XPathResultType.String, and read the result through StringValue rather than a node iterator.

The relative expression .//Car[descendant::Model > 2005 and descendant::Price < 25000]/@CarID then selects the CarID attributes of matching cars within that dealer. The leading dot uses the current dealer as the starting context, and @CarID selects the attribute nodes.

 1// Query and extract XML data using XPath expressions
 2
 3// Create an instance of a document
 4using (HTMLDocument doc = new HTMLDocument(Path.Combine(DataDir, "cars.xml")))
 5{
 6    // Select dealers that match XPath expression
 7    IXPathResult dealers = doc.Evaluate("//Dealer[descendant::Car[descendant::Model > 2005 and descendant::Price < 25000]]", doc, doc.CreateNSResolver(doc), XPathResultType.Any, null);
 8    Node dealer;
 9
10    // Iterate over the selected dealers
11    while ((dealer = dealers.IterateNext()) != null)
12    {
13        // Get and print Dealer name and Telephone
14        IXPathResult dealerInfo = doc.Evaluate("concat('Dealer name: ', Name/text(), ' Telephone: ', Telephone/text())", dealer, doc.CreateNSResolver(doc), XPathResultType.String, null);
15        Console.WriteLine(dealerInfo.StringValue);
16
17        // Select and print CarID that match XPath expression
18        IXPathResult carIds = doc.Evaluate(".//Car[descendant::Model > 2005 and descendant::Price < 25000]/@CarID", dealer, doc.CreateNSResolver(doc), XPathResultType.Any, null);
19        Node carId;
20
21        while ((carId = carIds.IterateNext()) != null)
22        {
23            Console.WriteLine("Car id: " + carId.TextContent);
24        }
25    }
26}

For cars.xml, the example prints the name and phone number of each matching dealer, followed by its matching car ID. The results are DealerName1 with car ID 1 and DealerName2 with car ID 2.

XPath Predicates, Attributes, and Relative Paths

The following XPath syntax is used throughout the examples:

SyntaxPurposeExample
[...]Filters a node-set by a condition//Car[CarInfo/Model > 2005]
@Selects an attribute@CarID
text()Selects text-node childrenName/text()
.Refers to the current context node.//Car/@CarID

An absolute location path starts from the document node. The abbreviated absolute path //Dealer, used in this article, selects Dealer descendants anywhere in the loaded document.

A relative expression is evaluated from the supplied context node and does not start with /. In the second C# example, Name/text() selects a direct child of the current dealer, while .//Car/@CarID selects attributes below that dealer. The expression .. refers to the parent node; for example, when Name is the context node, ../Telephone selects its Telephone sibling through their common parent. Pass the intended context node as the second argument to Document.Evaluate().

FAQ

How do I select all XML nodes with a specific name?

Use an expression such as //Dealer and pass it to Document.Evaluate() with XPathResultType.Any. Retrieve the matched nodes with IXPathResult.IterateNext().

How do I filter XML nodes by child values?

Use XPath predicates, for example //Dealer[descendant::Car[descendant::Model > 2005]], to select only nodes that match the condition.

How do I extract an attribute from selected XML nodes?

Use an attribute expression such as .//Car[descendant::Model > 2005]/@CarID relative to the current selected node.

What XPath version does Aspose.HTML for .NET support?

Aspose.HTML for .NET evaluates XPath 1.0 expressions against the document DOM, as documented for IXPathResult.

Related Articles