/** * Create a {@link KeyIndexIterator} that iterates over the nodes that result from a reference to * the XSLT <code>key</code> function or XPath <code>id</code> function. * * @param keyValue A string or iterator representing the key values or id references * @param isKeyCall A <code>boolean</code> indicating whether the iterator is being created for a * reference <code>key</code> or <code>id</code> */ public KeyIndexIterator getKeyIndexIterator(Object keyValue, boolean isKeyCall) { if (keyValue instanceof DTMAxisIterator) { return getKeyIndexIterator((DTMAxisIterator) keyValue, isKeyCall); } else { return getKeyIndexIterator(BasisLibrary.stringF(keyValue, _dom), isKeyCall); } }
/** * Evaluate the reference to the <code>key</code> or <code>id</code> function with the context * specified by {@link #setStartNode(int)} and set up this iterator to iterate over the DTM * nodes that are to be returned. */ protected void init() { super.init(); _position = 0; // All nodes retrieved are in the same document int rootHandle = _dom.getAxisIterator(Axis.ROOT).setStartNode(_startNode).next(); // Is the argument not a node set? if (_keyValueIterator == null) { // Look up nodes returned for the single string argument _nodes = lookupNodes(rootHandle, _keyValue); if (_nodes == null) { _nodes = EMPTY_NODES; } } else { DTMAxisIterator keyValues = _keyValueIterator.reset(); int retrievedKeyValueIdx = 0; boolean foundNodes = false; _nodes = null; // For each node in the node set argument, get the string value // and look up the nodes returned by key or id for that string // value. If at most one string value has nodes associated, // the nodes will be stored in _nodes; otherwise, the nodes // will be placed in a heap. for (int keyValueNode = keyValues.next(); keyValueNode != DTMAxisIterator.END; keyValueNode = keyValues.next()) { String keyValue = BasisLibrary.stringF(keyValueNode, _dom); IntegerArray nodes = lookupNodes(rootHandle, keyValue); if (nodes != null) { if (!foundNodes) { _nodes = nodes; foundNodes = true; } else { if (_nodes != null) { addHeapNode(new KeyIndexHeapNode(_nodes)); _nodes = null; } addHeapNode(new KeyIndexHeapNode(nodes)); } } } if (!foundNodes) { _nodes = EMPTY_NODES; } } }