From e6ff84b22248c3c66b7d3fd619132e48a89db5ef Mon Sep 17 00:00:00 2001 From: bculkin2442 Date: Mon, 29 Oct 2018 20:09:28 -0400 Subject: QueuedIterators QueuedIterators are iterators that can have other iterators interleaved into their iteration sequences. This was implemented as a decent idea, and because it may help get the iterative topDownTransform working again (if it ever worked in the first place...) --- .../main/java/bjc/utils/data/QueuedIterator.java | 171 +++++++++++++++++++++ .../java/bjc/utils/data/QueuedIteratorTest.java | 79 ++++++++++ 2 files changed, 250 insertions(+) create mode 100644 base/src/main/java/bjc/utils/data/QueuedIterator.java create mode 100644 base/src/test/java/bjc/utils/data/QueuedIteratorTest.java (limited to 'base/src') diff --git a/base/src/main/java/bjc/utils/data/QueuedIterator.java b/base/src/main/java/bjc/utils/data/QueuedIterator.java new file mode 100644 index 0000000..d75a9a3 --- /dev/null +++ b/base/src/main/java/bjc/utils/data/QueuedIterator.java @@ -0,0 +1,171 @@ +package bjc.utils.data; + +import java.util.ArrayDeque; +import java.util.Deque; +import java.util.Iterator; + +/** + * An iterator that supports queuing elements after/before the current iterator; + * + * @author bjculkin + * + * @param + */ +public class QueuedIterator implements Iterator { + private Iterator cur; + + private Deque> pending; + + /** + * Static method for constructing iterators. + * + * @return A queued iterator. + */ + public static QueuedIterator queued() { + return new QueuedIterator<>(); + } + + /** + * Static method for constructing iterators. + * + * @param itrs + * The iterators to use. + * @return A queued iterator over the provided iterators. + */ + @SafeVarargs + public static QueuedIterator queued(Iterator... itrs) { + return new QueuedIterator<>(itrs); + } + + /** + * Static method for constructing iterators. + * + * @param itrs + * The iterables to use. + * @return A queued iterator over the provided iterables. + */ + @SafeVarargs + public static QueuedIterator queued(Iterable... itrs) { + return new QueuedIterator<>(itrs); + } + + /** + * Create a new queued iterator that starts blank. + */ + public QueuedIterator() { + pending = new ArrayDeque<>(); + } + + /** + * Create a new queued iterator with a set of initial sources. + * + * @param inits + * The set of initial iterators to use. + */ + @SafeVarargs + public QueuedIterator(Iterator... inits) { + this(); + + for (Iterator init : inits) { + pending.add(init); + } + } + + /** + * Create a new queued iterator with a set of initial sources. + * + * @param inits + * The set of initial iterables to use. + */ + @SafeVarargs + public QueuedIterator(Iterable... inits) { + this(); + + for (Iterable init : inits) { + pending.add(init.iterator()); + } + } + + /** + * Add a new iterator who we will iterate through first. + * + * @param itr + * The iterator to go through first. + */ + public void before(Iterator itr) { + pending.push(cur); + + cur = itr; + } + + /** + * Add a new iterable who we will iterate through first. + * + * @param itr + * The iterable to go through first. + */ + public void before(Iterable itr) { + before(itr.iterator()); + } + + /** + * Add a new iterator who we will iterate through next. + * + * @param itr + * The iterator to go through next. + */ + public void after(Iterator itr) { + pending.push(itr); + } + /** + * Add a new iterable who we will iterate through next. + * + * @param itr + * The iterable to go through next. + */ + public void after(Iterable itr) { + after(itr.iterator()); + } + + /** + * Add a new iterator who we will iterate through last. + * + * @param itr + * The iterator to go through last. + */ + public void last(Iterator itr) { + pending.add(itr); + } + + /** + * Add a new iterable who we will iterate through last. + * + * @param itr + * The iterable to go through last. + */ + public void last(Iterable itr) { + last(itr.iterator()); + } + @Override + public boolean hasNext() { + while (cur == null || !cur.hasNext()) { + if (pending.isEmpty()) return false; + + cur = pending.pop(); + } + + return cur.hasNext(); + } + + @Override + public E next() { + while (cur == null || !cur.hasNext()) { + if (pending.isEmpty()) return null; + + cur = pending.pop(); + } + + return cur.next(); + } + +} diff --git a/base/src/test/java/bjc/utils/data/QueuedIteratorTest.java b/base/src/test/java/bjc/utils/data/QueuedIteratorTest.java new file mode 100644 index 0000000..573d218 --- /dev/null +++ b/base/src/test/java/bjc/utils/data/QueuedIteratorTest.java @@ -0,0 +1,79 @@ +package bjc.utils.data; + +import static org.junit.Assert.*; + +import java.util.Iterator; + +import static java.util.Arrays.asList; + +import org.junit.Test; + +import bjc.utils.funcutils.TestUtils; + +import static bjc.utils.data.QueuedIterator.*; +import static bjc.utils.funcutils.TestUtils.*; +import static bjc.utils.funcutils.IteratorUtils.*; + +/** + * Test of QueuedIterator. + * + * @author bjculkin + * + */ +public class QueuedIteratorTest { + + /** + * Test of functionality. + */ + @Test + public void test() { + assertIteratorEquals(false, queued()); + + assertIteratorEquals(false, queued(asList(1, 2, 3)), 1, 2, 3); + assertIteratorEquals(false, queued(asList(1, 2, 3), asList(3, 2, 1)), 1, 2, 3, 3, 2, 1); + + } + + /** + * Test of before() method. + */ + @Test + public void testBefore() { + QueuedIterator itr = queued(asList(1, 2, 3)); + + assertIteratorEquals(true, itr, 1, 2); + + itr.before(asList(1, 2, 3)); + + assertIteratorEquals(false, itr, 1, 2, 3, 3); + } + + /** + * Test of after() method. + */ + @Test + public void testAfter() { + QueuedIterator itr = queued(asList(1, 2, 3)); + + assertIteratorEquals(true, itr, 1, 2); + + itr.after(asList(1, 2, 3)); + + assertIteratorEquals(false, itr, 3, 1, 2, 3); + } + + /** + * Test of last() method. + */ + @Test + public void testLast() { + QueuedIterator itr = queued(asList(1, 2, 3)); + + assertIteratorEquals(true, itr, 1, 2); + + itr.after(asList(4)); + itr.last(asList(1, 2, 3)); + + assertIteratorEquals(false, itr, 3, 4, 1, 2, 3); + } +} -- cgit v1.2.3