Provides support for common XPath axis and filtering functions,
via a native-D interface instead of typical interpreted notation.
The general idea here is to generate a NodeSet consisting of those
tree-nodes which satisfy a filtering function. The direction, or
axis, of tree traversal is governed by one of several predefined
operations. All methods facilitiate call-chaining, where each step
returns a new NodeSet instance to be operated upon.
The set of nodes themselves are collected in a freelist, avoiding
heap-activity and making good use of D array-slicing facilities.
XPath examples
autodoc = newDocument!(char);
// attach an element with some attributes, plus// a child element with an attached data valuedoc.tree.element (null, "element")
.attribute (null, "attrib1", "value")
.attribute (null, "attrib2")
.element (null, "child", "value");
// select named-elementsautoset = doc.query["element"]["child"];
// select all attributes named "attrib1"set = doc.query.descendant.attribute("attrib1");
// select elements with one parent and a matching text valueset = doc.query[].filter((doc.Noden) {returnn.children.hasData("value");});
Note that path queries are temporal - they do not retain content
across mulitple queries. That is, the lifetime of a query result
is limited unless you explicitly copy it. For example, this will
fail to operate as one might expect
Each of the above accept an optional string, which is used in an
axis-specific way to filter nodes. For instance, a .child("food")
will filter <food> child elements. These variants are shortcuts
to using a filter to post-process a result. Each of the above also
have variants which accept a delegate instead.
In general, you traverse an axis and operate upon the results. The
operation applied may be another axis traversal, or a filtering
step. All steps can be, and generally should be chained together.
Filters are implemented via a delegate mechanism
.filter (booldelegate(Node))
Where the delegate returns true if the node passes the filter. An
example might be selecting all nodes with a specific attribute
Obviously this is not as clean and tidy as true XPath notation, but
that can be wrapped atop this API instead. The benefit here is one
of raw throughput - important for some applications.
Note that every operation returns a discrete result. Methods first()
and last() also return a set of one or zero elements. Some language
specific extensions are provided for too
* .child() canbesubstitutedwith [] notationinstead
* [] notationcanbeusedtoindexaspecificelement, like .nth()
* the .nodesattributeexposesanunderlyingNode[], whichmaybeslicedortraversedintheusualDmanner
Other (query result) utility methods include
.dup
.first
.last
.opIndex
.nth
.count
.opApply
XmlPath itself needs to be a class in order to avoid forward-ref issues.
XPath support
Provides support for common XPath axis and filtering functions, via a native-D interface instead of typical interpreted notation.
The general idea here is to generate a NodeSet consisting of those tree-nodes which satisfy a filtering function. The direction, or axis, of tree traversal is governed by one of several predefined operations. All methods facilitiate call-chaining, where each step returns a new NodeSet instance to be operated upon.
The set of nodes themselves are collected in a freelist, avoiding heap-activity and making good use of D array-slicing facilities.
XPath examples
Note that path queries are temporal - they do not retain content across mulitple queries. That is, the lifetime of a query result is limited unless you explicitly copy it. For example, this will fail to operate as one might expect
The above will lose elements, because the associated document reuses node space for subsequent queries. In order to retain results, do this
The above .dup is generally very small (a set of pointers only). On the other hand, recursive queries are fully supported
Typical usage tends to exhibit the following pattern, Where each query result is processed before another is initiated
Supported axis include:
Each of the above accept an optional string, which is used in an axis-specific way to filter nodes. For instance, a .child("food") will filter <food> child elements. These variants are shortcuts to using a filter to post-process a result. Each of the above also have variants which accept a delegate instead.
In general, you traverse an axis and operate upon the results. The operation applied may be another axis traversal, or a filtering step. All steps can be, and generally should be chained together. Filters are implemented via a delegate mechanism
Where the delegate returns true if the node passes the filter. An example might be selecting all nodes with a specific attribute
Obviously this is not as clean and tidy as true XPath notation, but that can be wrapped atop this API instead. The benefit here is one of raw throughput - important for some applications.
Note that every operation returns a discrete result. Methods first() and last() also return a set of one or zero elements. Some language specific extensions are provided for too
Other (query result) utility methods include
XmlPath itself needs to be a class in order to avoid forward-ref issues.