package org.basex.query.iter; import org.basex.query.QueryException; import org.basex.query.item.Empty; import org.basex.query.item.Item; import org.basex.query.item.Seq; import org.basex.query.item.Value; import org.basex.util.Array; /** * Iterator interface. * * @author BaseX Team 2005-12, BSD License * @author Christian Gruen */ public abstract class Iter { /** * Returns the next item or {@code null} if no other items are found. * @return resulting item or {@code null} * @throws QueryException query exception */ public abstract Item next() throws QueryException; /** * Returns the specified item, or an arbitrary item if the index is invalid. * This method needs to be implemented - and should only be called - if * {@link Iter#size} returns the correct number of results. A calling method * should call {@link #reset} after the last items has been retrieved. * @param i value offset * @return specified item * @throws QueryException query exception */ @SuppressWarnings("unused") public Item get(final long i) throws QueryException { return null; } /** * Returns the iterator size. Note: {@code -1} is returned if the * result size is unknown. If this method is implemented by an iterator, * {@link #get} needs to be implemented as well. * @return number of entries */ public long size() { return -1; } /** * Resets the iterator and returns {@code true} if operation was successful. * {@code false} is returned if the iterator cannot be reset. * @return true if operator could be reset */ public boolean reset() { return false; } /** * Returns a sequence with all iterator values. * Must only be called if {@link #next} has not been called before. * @return sequence * @throws QueryException query exception */ public Value value() throws QueryException { // check if sequence is empty Item i = next(); if(i == null) return Empty.SEQ; // if possible, allocate array with final size, and add all single items Item[] item = new Item[Math.max(1, (int) size())]; int s = 0; do { if(s == item.length) item = extend(item); item[s++] = i; } while((i = next()) != null); // create final value return Seq.get(item, s); } /** * Doubles the size of an item array. * @param it item array * @return resulting array */ static Item[] extend(final Item[] it) { final int s = it.length; final Item[] tmp = new Item[Array.newSize(s)]; System.arraycopy(it, 0, tmp, 0, s); return tmp; } }