Iter implements Iterator<T> { public static <T> Optional<T> min(Iterator<T> iter, Comparator<T> comparator) { T x = null; while(iter.hasNext()) { T elt = iter.next(); if ( x == null ) x = elt; else { int cmp = comparator.compare(x, elt); if ( cmp > 0 ) x = elt; } } return Optional.ofNullable(x); } private  Iter(Iterator<T> iterator); static void forEach(Iterator<T> iter, Consumer<T> action); static Stream<T> asStream(Iterator<T> iterator); static Stream<T> asStream(Iterator<T> iterator, boolean parallel); static Iterator<T> singleton(T item); static Iterator<T> nullIterator(); static Set<T> toSet(Iterator<? extends T> stream); static List<T> toList(Iterator<? extends T> stream); static Iterator<T> iterator(Iterator<? extends T> iterator); static R foldLeft(Iterator<? extends T> stream, R value, Folder<T, R> function); static R foldRight(Iterator<? extends T> stream, R value, Folder<T, R> function); static Optional<T> reduce(Iterator<T> iter, BinaryOperator<T> accumulator); static T reduce(Iterator<T> iter, T identity, BinaryOperator<T> accumulator); static Optional<T> min(Iterator<T> iter, Comparator<T> comparator); static Optional<T> max(Iterator<T> iter, Comparator<T> comparator); static R collect(Iterator<T> iter, Supplier<R> supplier, BiConsumer<R, ? super T> accumulator); static R collect(Iterator<T> iter, Collector<? super T, A, R> collector); static void apply(Iterator<? extends T> stream, Consumer<T> action); static Iterator<T> filter(final Iterator<? extends T> stream, final Predicate<T> filter); static Iterator<T> notFilter(final Iterator<? extends T> stream, final Predicate<T> filter); @Deprecated static boolean every(Iterator<? extends T> iter, Predicate<T> predicate); static boolean allMatch(Iterator<T> iter, Predicate<? super T> predicate); @Deprecated static boolean some(Iterator<T> iter, Predicate<? super T> predicate); static boolean anyMatch(Iterator<T> iter, Predicate<? super T> predicate); static boolean noneMatch(Iterator<T> iter, Predicate<? super T> predicate); static Optional<T> findFirst(Iterator<T> iter, Predicate<? super T> predicate); static Optional<T> findAny(Iterator<T> iter, Predicate<? super T> predicate); static Iterator<R> map(Iterator<? extends T> stream, Function<T, R> converter); @Deprecated static List<R> map(List<? extends T> list, Function<T, R> converter); static Iterator<R> flatMap(Iterator<T> iter, Function<T, Iterator<R>> mapper); static Iterator<T> operate(final Iterator<? extends T> stream, final Consumer<T> action); static Iterator<T> printWrapper(final Iterator<? extends T> stream); static Iterator<T> printWrapper(final PrintStream out, final Iterator<? extends T> stream); static Iterator<T> append(Iterator<? extends T> iter1, Iterator<? extends T> iter2); static Iterator<T> distinct(Iterator<T> iter); static Iterator<T> distinctAdjacent(Iterator<T> iter); static Iterator<T> removeNulls(Iterator<T> iter); static int step(Iterator<?> iter, int steps); static List<T> take(Iterator<T> iter, int N); static Iterator<T> takeWhile(Iterator<T> iter, Predicate<T> predicate); static Iterator<T> takeUntil(Iterator<T> iter, Predicate<T> predicate); static Iterator<T> dropWhile(Iterator<T> iter, Predicate<T> predicate); static Iterator<T> dropUntil(Iterator<T> iter, Predicate<T> predicate); static Iterator<X> limit(Iterator<X> iterator, long limit); static Iterator<X> skip(Iterator<X> iterator, long limit); static long count(Iterator<T> iterator); static void consume(Iterator<T> iterator); static String asString(Iterator<T> stream, String sep); static String asString(Iterator<T> stream, CharSequence sep, CharSequence prefix, CharSequence suffix); static void close(Iterator<T> iter); static Iterator<T> log(Iterator<T> stream); static Iterator<T> log(final PrintStream out, Iterator<T> stream); static Iterator<T> debug(Iterator<T> stream); static Iterator<T> debug(final PrintStream out, Iterator<T> stream); static void print(Iterator<T> stream); static void print(final PrintStream out, Iterator<T> stream); static void sendToSink(Iterator<T> iter, Sink<T> sink); @Deprecated static void sendToSink(Iterable<T> stream, Sink<T> sink); static Iter<T> iter(Iter<T> iter); static Iter<T> iter(Collection<T> collection); static Iter<T> iter(Iterator<T> iterator); static Iter<T> singletonIter(T item); static Iter<T> nullIter(); static Iterator<T> materialize(Iterator<T> iter); static Iter<T> concat(Iter<T> iter1, Iter<T> iter2); static Iter<T> concat(Iterator<T> iter1, Iterator<T> iter2); static T first(Iterator<T> iter); static T first(Iterator<T> iter, Predicate<T> filter); @Deprecated static T first(Collection<T> collection, Predicate<T> filter); static int firstIndex(Iterator<T> iter, Predicate<T> filter); @Deprecated static int firstIndex(Collection<T> collection, Predicate<T> filter); static T last(Iterator<T> iter); static T last(Iterator<T> iter, Predicate<T> filter); @Deprecated static T last(Collection<T> collection, Predicate<T> filter); static int lastIndex(Iterator<T> iter, Predicate<T> filter); @Deprecated static int lastIndex(Collection<T> collection, Predicate<T> filter); void forEach(Consumer<T> action); Set<T> toSet(); List<T> toList(); void sendToSink(Sink<T> sink); T first(); T last(); T first(Predicate<T> filter); int firstIndex(Predicate<T> filter); T last(Predicate<T> filter); int lastIndex(Predicate<T> filter); Iter<T> filter(Predicate<T> filter); boolean every(Predicate<T> predicate); boolean some(Predicate<T> filter); boolean allMatch(Predicate<? super T> predicate); boolean anyMatch(Predicate<? super T> predicate); boolean noneMatch(Predicate<? super T> predicate); Optional<T> findFirst(Predicate<? super T> predicate); Optional<T> findAny(Predicate<? super T> predicate); Iter<T> removeNulls(); Iter<R> map(Function<T, R> converter); Iter<R> flatMap(Function<T, Iterator<R>> converter); Iter<T> operate(Consumer<T> action); R foldLeft(R initial, Folder<T, R> accumulator); R foldRight(R initial, Folder<T, R> accumulator); Optional<T> reduce(BinaryOperator<T> accumulator); T reduce(T identity, BinaryOperator<T> accumulator); Optional<T> min(Comparator<T> comparator); Optional<T> max(Comparator<T> comparator); R collect(Supplier<R> supplier, BiConsumer<R, T> accumulator/*, BiConsumer<R, R> combiner*/); R collect(Collector<? super T, A, R> collector); void apply(Consumer<T> action); Iter<T> append(Iterator<T> iter); Iter<T> take(int N); Iter<T> takeWhile(Predicate<T> predicate); Iter<T> takeUntil(Predicate<T> predicate); Iter<T> dropWhile(Predicate<T> predicate); Iter<T> dropUntil(Predicate<T> predicate); Iter<T> limit(long N); Iter<T> skip(long N); long count(); Iter<T> distinct(); Iter<T> distinctAdjacent(); @Override boolean hasNext(); @Override T next(); @Override void remove();  }
@Test public void min1() { Optional<String> x = Iter.min(data(), String::compareTo); assertFalse(x.isPresent()); }
@Test public void min2() { Optional<String> x = Iter.min(data("2"), String::compareTo); assertTrue(x.isPresent()); assertEquals("2", x.get()); }
@Test public void min3() { Optional<String> x = Iter.min(data("1", "2", "3"), String::compareTo); assertTrue(x.isPresent()); assertEquals("1", x.get()); }
@Test public void min4() { Optional<String> x = Iter.min(data("3", "1", "2"), String::compareTo); assertTrue(x.isPresent()); assertEquals("1", x.get()); }