001    /*
002     * Licensed to the Apache Software Foundation (ASF) under one
003     * or more contributor license agreements. See the NOTICE file
004     * distributed with this work for additional information
005     * regarding copyright ownership. The ASF licenses this file
006     * to you under the Apache License, Version 2.0 (the  "License");
007     * you may not use this file except in compliance with the License.
008     * You may obtain a copy of the License at
009     *
010     *     http://www.apache.org/licenses/LICENSE-2.0
011     *
012     * Unless required by applicable law or agreed to in writing, software
013     * distributed under the License is distributed on an "AS IS" BASIS,
014     * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
015     * See the License for the specific language governing permissions and
016     * limitations under the License.
017     */
018    /*
019     * $Id: UnionIterator.java 468651 2006-10-28 07:04:25Z minchau $
020     */
021    
022    package org.apache.xalan.xsltc.dom;
023    
024    import org.apache.xalan.xsltc.DOM;
025    import org.apache.xalan.xsltc.runtime.BasisLibrary;
026    import org.apache.xml.dtm.DTMAxisIterator;
027    import org.apache.xml.dtm.ref.DTMAxisIteratorBase;
028    
029    /**
030     * UnionIterator takes a set of NodeIterators and produces
031     * a merged NodeSet in document order with duplicates removed
032     * The individual iterators are supposed to generate nodes
033     * in document order
034     * @author Jacek Ambroziak
035     * @author Santiago Pericas-Geertsen
036     */
037    public final class UnionIterator extends MultiValuedNodeHeapIterator {
038        /** wrapper for NodeIterators to support iterator
039            comparison on the value of their next() method
040        */
041        final private DOM _dom;
042    
043        private final class LookAheadIterator
044                extends MultiValuedNodeHeapIterator.HeapNode
045        {
046            public DTMAxisIterator iterator;
047                    
048            public LookAheadIterator(DTMAxisIterator iterator) {
049                super();
050                this.iterator = iterator;
051            }
052                    
053            public int step() {
054                _node = iterator.next();
055                return _node;
056            }
057    
058            public HeapNode cloneHeapNode() {
059                LookAheadIterator clone = (LookAheadIterator) super.cloneHeapNode();
060                clone.iterator = iterator.cloneIterator();
061                return clone;
062            }
063    
064            public void setMark() {
065                super.setMark();
066                iterator.setMark();
067            }
068    
069            public void gotoMark() {
070                super.gotoMark();
071                iterator.gotoMark();
072            }
073    
074            public boolean isLessThan(HeapNode heapNode) {
075                LookAheadIterator comparand = (LookAheadIterator) heapNode;
076                return _dom.lessThan(_node, heapNode._node);
077            }
078    
079            public HeapNode setStartNode(int node) {
080                iterator.setStartNode(node);
081                return this;
082            }
083    
084            public HeapNode reset() {
085                iterator.reset();
086                return this;
087            }
088        } // end of LookAheadIterator
089    
090        public UnionIterator(DOM dom) {
091            _dom = dom;
092        }
093    
094        public UnionIterator addIterator(DTMAxisIterator iterator) {
095            addHeapNode(new LookAheadIterator(iterator));
096            return this;
097        }
098    }