Merge branch 'deprecate-find-xx-of-any-type' into analysis-listener
This commit is contained in:
commit
dfffaf772c
5 files changed
+180
-9
No files matched your search
@@ -46,6 +46,25 @@ Support for XPath versions 1.0, 1.0-compatibility was removed, support for XPath
|
||||
* The deprecated support for sequence-valued attributes is removed. Sequence-valued properties are still supported.
|
||||
* Refer to [the Saxonica documentation](https://www.saxonica.com/html/documentation/expressions/xpath31new.html) for an introduction to new features in XPath 3.1.
|
||||
|
||||
|
||||
#### Node stream API
|
||||
|
||||
This version includes a powerful API to navigate trees, similar in usage to the Java 8 Stream API:
|
||||
```java
|
||||
node.descendants(ASTMethodCall.class)
|
||||
.filter(m -> "toString".equals(m.getMethodName()))
|
||||
.map(m -> m.getQualifier())
|
||||
.filter(q -> TypeTestUtil.isA(String.class, q))
|
||||
.foreach(System.out::println);
|
||||
```
|
||||
|
||||
A pipeline like shown here traverses the tree lazily, which is more efficient than traversing eagerly to put all descendants in a list. It is also much easier to change than the old imperative way.
|
||||
|
||||
To make this API as accessible as possible, the {% jdoc core::lang.ast.Node %} interface has been fitted with new methods producing node streams. Those methods replace previous tree traversal methods like `Node#findDescendantsOfType`. In all cases, they should be more efficient and more convenient.
|
||||
|
||||
See {% jdoc core::lang.ast.NodeStream %} for more details.
|
||||
|
||||
|
||||
#### JavaScript support
|
||||
|
||||
The JS specific parser options have been removed. The parser now always retains comments and uses version ES6.
|
||||
|
||||
File diff suppressed because it is too large.
Load diff
@@ -183,4 +183,20 @@ public abstract class AbstractNode<B extends AbstractNode<B, N>, N extends Gener
|
||||
return getXPathNodeName();
|
||||
}
|
||||
|
||||
@Override
|
||||
@SuppressWarnings("unchecked")
|
||||
public final <R extends Node> @Nullable R firstChild(Class<? extends R> rClass) {
|
||||
// This operation is extremely common so we give it an optimal
|
||||
// implementation, based directly on the array. This will never
|
||||
// create a node stream object, and array bounds are not checked.
|
||||
// It's final so it can be inlined.
|
||||
for (Node child : children) {
|
||||
if (rClass.isInstance(child)) {
|
||||
// rClass.cast(child) is more expensive than this
|
||||
// unchecked cast, which we know is safe.
|
||||
return (R) child;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
||||
@@ -83,4 +83,14 @@ public interface GenericNode<N extends GenericNode<N>> extends Node {
|
||||
default NodeStream<N> ancestors() {
|
||||
return (NodeStream<N>) Node.super.ancestors();
|
||||
}
|
||||
|
||||
@Override
|
||||
default @Nullable N getPreviousSibling() {
|
||||
return (N) Node.super.getPreviousSibling();
|
||||
}
|
||||
|
||||
@Override
|
||||
default @Nullable N getNextSibling() {
|
||||
return (N) Node.super.getNextSibling();
|
||||
}
|
||||
}
|
||||
+1
-1
@@ -162,7 +162,7 @@ final class SingletonNodeStream<T extends Node> extends IteratorBasedNStream<T>
|
||||
|
||||
@Override
|
||||
public <R extends Node> NodeStream<R> firstChild(Class<? extends R> rClass) {
|
||||
return NodeStream.of(TraversalUtils.getFirstChildMatching(node, Filtermap.isInstance(rClass), 0, node.getNumChildren()));
|
||||
return NodeStream.of(node.firstChild(rClass));
|
||||
}
|
||||
|
||||
@Override
|
||||
|
||||
Reference in new issue
Block a user