Skip to content
ChuckSavage edited this page May 26, 2012 · 5 revisions

XPath is a very versitile short-hand notation for selecting nodes in an XML file. As of .Net 3.5, there was no XElement.XPath() functionality. This is an attempt to add some XPath functionality to XElement's. There is much work to be done to complete the XPath specification.

Extensions

Because C# doesn't differentiate between two methods that have the same parameters but different results, the two method signatures are XPath() and XPathElement(). XPathElement is simply a call to XPath with .FirstOrDefault() applied to the result.

XPath

Example: Find all persons who are 30 years and older. Uses the Birth attribute value. By supplying a DateTime comparison value, the value in the Birth attribute will be converted to a DateTime for the comparison!

root.XPath("people/person[@Birth<={0}]", DateTime.Now.AddYears(-30));

The second argument defines the type to compare against as well as the value.

public static IEnumerable<XElement> XPath(this XElement source, XPathString path, bool create)
{
    return cXPath.Enumerable(source, path, create);
}

public static IEnumerable<XElement> XPath(this XElement source, string path, params object[] args)
{
    return XPath(source, new XPathString(path, args), true);
}

create: (default) true - will create empty elements if a path/to/node doesn't exist. This prevents null exceptions from being thrown. Internal XPath strings, such as [path/to/node=5] will create the node anyway (currently).

returns: an IEnumerable<XElement> list of found nodes.

XPathElement

Example: Find the record of the person with the id person.Id. Uses the person's child node named id value.

root.XPathElement("people/person[id={0}]", person.Id);

The second argument defines the type to compare against as well as the value.

public static XElement XPathElement(this XElement source, XPathString path, bool create)
{
    return XPath(source, path, create).FirstOrDefault();
}

public static XElement XPathElement(this XElement source, string path, params object[] args)
{
    return XPathElement(source, new XPathString(path, args), true);
}

create: (default) true - will create empty elements if a path/to/node doesn't exist. This prevents null exceptions from being thrown. Internal XPath strings, such as [path/to/node=5] will create the node anyway (currently).

returns: a single Element.

So if the XPath() call returns more than one result, the first value found is returned. You've likely defined your search too broad if XPath() returned more than one.

Functions

Max

Syntax: XElement max = root.XPathElement("node[max(@attrib, {0}]", int.MinValue);

The value argument to max(key, value) is the type to use for comparison as well as the default value if the Attribute attrib doesn't exist for the node.

Syntax: XElement max = root.XPathElement("node[max(child, {0}]", int.MinValue);

The value argument to max(key, value) is the type to use for comparison as well as the default value if the Element child doesn't exist for the node.

Min

Syntax: XElement min = root.XPathElement("node[min(@attrib, {0}]", int.MaxValue);

The value argument to max(key, value) is the type to use for comparison as well as the default value if the Attribute attrib doesn't exist for the node.

Syntax: XElement min = root.XPathElement("node[min(child, {0}]", int.MaxValue);

The value argument to max(key, value) is the type to use for comparison as well as the default value if the Element child doesn't exist for the node.

Starts-With

Syntax: var values = root.XPath("node[starts-with(child, 'ABC')]");

starts-with(key, value) Key: can be * for any child node, or @* for any attribute, or the name of the attribute or child node to get the value from. The result is any node that matches the attribute or child node's Value property.

Clone this wiki locally