Home | History | Annotate | Download | only in stream
      1 /*
      2  * Copyright (c) 1997, 2013, Oracle and/or its affiliates. All rights reserved.
      3  * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
      4  *
      5  * This code is free software; you can redistribute it and/or modify it
      6  * under the terms of the GNU General Public License version 2 only, as
      7  * published by the Free Software Foundation.
      8  *
      9  * This code is distributed in the hope that it will be useful, but WITHOUT
     10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
     11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
     12  * version 2 for more details (a copy is included in the LICENSE file that
     13  * accompanied this code).
     14  *
     15  * You should have received a copy of the GNU General Public License version
     16  * 2 along with this work; if not, write to the Free Software Foundation,
     17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
     18  *
     19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
     20  * or visit www.oracle.com if you need additional information or have any
     21  * questions.
     22  */
     23 package org.openjdk.testlib.java.util.stream;
     24 
     25 import java.util.*;
     26 import java.util.stream.*;
     27 import java.util.function.BiConsumer;
     28 import java.util.function.BiPredicate;
     29 import java.util.function.BinaryOperator;
     30 import java.util.function.Consumer;
     31 import java.util.function.DoubleBinaryOperator;
     32 import java.util.function.DoubleConsumer;
     33 import java.util.function.DoublePredicate;
     34 import java.util.function.Function;
     35 import java.util.function.IntBinaryOperator;
     36 import java.util.function.IntConsumer;
     37 import java.util.function.IntFunction;
     38 import java.util.function.IntPredicate;
     39 import java.util.function.IntUnaryOperator;
     40 import java.util.function.LongBinaryOperator;
     41 import java.util.function.LongConsumer;
     42 import java.util.function.LongPredicate;
     43 import java.util.function.Predicate;
     44 import java.util.function.Supplier;
     45 import java.util.function.ToDoubleFunction;
     46 import java.util.function.ToIntFunction;
     47 import java.util.function.ToLongFunction;
     48 
     49 import static org.testng.Assert.assertEquals;
     50 import static org.testng.Assert.assertTrue;
     51 
     52 /**
     53  * LambdaTestHelpers -- assertion methods and useful objects for lambda test cases
     54  */
     55 public class LambdaTestHelpers {
     56     public static final String LONG_STRING = "When in the Course of human events it becomes necessary for one people to dissolve the political bands which have connected them with another and to assume among the powers of the earth, the separate and equal station to which the Laws of Nature and of Nature's God entitle them, a decent respect to the opinions of mankind requires that they should declare the causes which impel them to the separation.";
     57 
     58     @SuppressWarnings("rawtypes")
     59     public static final Consumer bEmpty = x -> {  };
     60     @SuppressWarnings("rawtypes")
     61     public static final IntConsumer bIntEmpty = x -> {  };
     62     @SuppressWarnings("rawtypes")
     63     public static final BiConsumer bBiEmpty = (x,y) -> { };
     64     @SuppressWarnings("rawtypes")
     65     public static final Consumer bHashCode = x -> { Objects.hashCode(x); };
     66     @SuppressWarnings("rawtypes")
     67     public static final BiConsumer bBiHashCode = (x,y) -> { Objects.hash(x, y); };
     68     public static final Function<Integer, Integer> mZero = x -> 0;
     69     public static final Function<Integer, Integer> mId = x -> x;
     70     public static final Function<Integer, Integer> mDoubler = x -> x * 2;
     71     public static final Function<Integer, Stream<Integer>> mfId = e -> Collections.singletonList(e).stream();
     72     public static final Function<Integer, Stream<Integer>> mfNull = e -> Collections.<Integer>emptyList().stream();
     73     public static final Function<Integer, Stream<Integer>> mfLt = e -> {
     74         List<Integer> l = new ArrayList<>();
     75         for (int i=0; i<e; i++)
     76             l.add(i);
     77         return l.stream();
     78     };
     79     public static final ToIntFunction<Integer> imDoubler = x -> x * 2;
     80     public static final ToLongFunction<Long> lmDoubler = x -> x * 2;
     81     public static final ToDoubleFunction<Double> dmDoubler = x -> x * 2;
     82     public static final Predicate<Integer> pFalse = x -> false;
     83     public static final Predicate<Integer> pTrue = x -> true;
     84     public static final Predicate<Integer> pEven = x -> 0 == x % 2;
     85     public static final Predicate<Integer> pOdd = x -> 1 == x % 2;
     86     public static final IntPredicate ipFalse = x -> false;
     87     public static final IntPredicate ipTrue = x -> true;
     88     public static final IntPredicate ipEven = x -> 0 == x % 2;
     89     public static final IntPredicate ipOdd = x -> 1 == x % 2;
     90     public static final LongPredicate lpFalse = x -> false;
     91     public static final LongPredicate lpTrue = x -> true;
     92     public static final LongPredicate lpEven = x -> 0 == x % 2;
     93     public static final LongPredicate lpOdd = x -> 1 == x % 2;
     94     public static final DoublePredicate dpFalse = x -> false;
     95     public static final DoublePredicate dpTrue = x -> true;
     96     public static final DoublePredicate dpEven = x -> 0 == ((long) x) % 2;
     97     public static final DoublePredicate dpOdd = x -> 1 == ((long) x) % 2;
     98     public static final BinaryOperator<Integer> rPlus = (x, y) -> x+y;
     99     public static final BinaryOperator<Integer> rMax = (x, y) -> Math.max(x, y);
    100     public static final BinaryOperator<Integer> rMin = (x, y) -> Math.min(x,y);
    101     public static final IntBinaryOperator irPlus = (x, y) -> x+y;
    102     public static final IntBinaryOperator irMax = (x, y) -> Math.max(x, y);
    103     public static final IntBinaryOperator irMin = (x, y) -> Math.min(x,y);
    104     public static final IntUnaryOperator irDoubler = x -> x * 2;
    105     public static final LongBinaryOperator lrPlus = (x, y) -> x+y;
    106     public static final DoubleBinaryOperator drPlus = (x, y) -> x+y;
    107     public static final Comparator<Integer> cInteger = (a, b) -> Integer.compare(a, b);
    108     public static final BiPredicate<?, ?> bipFalse = (x, y) -> false;
    109     public static final BiPredicate<?, ?> bipTrue = (x, y) -> true;
    110     public static final BiPredicate<Integer, Integer> bipBothEven = (x, y) -> 0 == (x % 2 + y % 2);
    111     public static final BiPredicate<Integer, Integer> bipBothOdd = (x, y) -> 2 == (x % 2 + y % 2);
    112     public static final BiPredicate<?, ?> bipSameString = (x, y) -> String.valueOf(x).equals(String.valueOf(y));
    113 
    114     public static final IntFunction<Integer[]> integerArrayGenerator = s -> new Integer[s];
    115 
    116     public static final IntFunction<Object[]> objectArrayGenerator = s -> new Object[s];
    117 
    118     public static final Function<String, Stream<Character>> flattenChars = string -> {
    119         List<Character> l = new ArrayList<>();
    120         for (int i=0; i<string.length(); i++)
    121             l.add(string.charAt(i));
    122         return l.stream();
    123     };
    124 
    125     public static final Function<String, IntStream> flattenInt
    126             = string -> IntStream.range(0, string.length()).map(string::charAt);
    127 
    128     public static <T, R> Function<T, R> forPredicate(Predicate<? super T> predicate, R forTrue, R forFalse) {
    129         Objects.requireNonNull(predicate);
    130 
    131         return t -> predicate.test(t) ? forTrue : forFalse;
    132     }
    133 
    134     public static <T> Function<T, T> identity() {
    135         return t -> t;
    136     }
    137 
    138     public static<V, T, R> Function<V, R> compose(Function<? super T, ? extends R> after, Function<? super V, ? extends T> before) {
    139         Objects.requireNonNull(before);
    140         return (V v) -> after.apply(before.apply(v));
    141     }
    142 
    143     public static List<Integer> empty() {
    144         ArrayList<Integer> list = new ArrayList<>();
    145         list.add(null);
    146         return list;
    147     }
    148 
    149     public static List<Integer> countTo(int n) {
    150         return range(1, n);
    151     }
    152 
    153     public static List<Integer> range(int l, int u) {
    154         ArrayList<Integer> list = new ArrayList<>(u - l + 1);
    155         for (int i=l; i<=u; i++) {
    156             list.add(i);
    157         }
    158         return list;
    159     }
    160 
    161     public static List<Integer> repeat(int value, int n) {
    162         ArrayList<Integer> list = new ArrayList<>(n);
    163         for (int i=1; i<=n; i++) {
    164             list.add(value);
    165         }
    166         return list;
    167     }
    168 
    169     public static List<Double> asDoubles(List<Integer> integers) {
    170         ArrayList<Double> list = new ArrayList<>();
    171         for (Integer i : integers) {
    172             list.add((double) i);
    173         }
    174         return list;
    175     }
    176 
    177     public static List<Long> asLongs(List<Integer> integers) {
    178         ArrayList<Long> list = new ArrayList<>();
    179         for (Integer i : integers) {
    180             list.add((long) i);
    181         }
    182         return list;
    183     }
    184 
    185     public static void assertCountSum(Stream<? super Integer> it, int count, int sum) {
    186         assertCountSum(it.iterator(), count, sum);
    187     }
    188 
    189     public static void assertCountSum(Iterable<? super Integer> it, int count, int sum) {
    190         assertCountSum(it.iterator(), count, sum);
    191     }
    192 
    193     public static void assertCountSum(Iterator<? super Integer> it, int count, int sum) {
    194         int c = 0;
    195         int s = 0;
    196         while (it.hasNext()) {
    197             int i = (Integer) it.next();
    198             c++;
    199             s += i;
    200         }
    201 
    202         assertEquals(c, count);
    203         assertEquals(s, sum);
    204     }
    205 
    206     public static void assertConcat(Iterator<Character> it, String result) {
    207         StringBuilder sb = new StringBuilder();
    208         while (it.hasNext()) {
    209             sb.append(it.next());
    210         }
    211 
    212         assertEquals(result, sb.toString());
    213     }
    214 
    215     public static<T extends Comparable<? super T>> void assertSorted(Iterator<T> i) {
    216         i = toBoxedList(i).iterator();
    217 
    218         if (!i.hasNext())
    219             return;
    220         T last = i.next();
    221         while (i.hasNext()) {
    222             T t = i.next();
    223             assertTrue(last.compareTo(t) <= 0);
    224             assertTrue(t.compareTo(last) >= 0);
    225             last = t;
    226         }
    227     }
    228 
    229     public static<T> void assertSorted(Iterator<T> i, Comparator<? super T> comp) {
    230         if (i instanceof PrimitiveIterator.OfInt
    231                 || i instanceof PrimitiveIterator.OfDouble
    232                 || i instanceof PrimitiveIterator.OfLong) {
    233             i = toBoxedList(i).iterator();
    234         }
    235 
    236         if (!i.hasNext())
    237             return;
    238         T last = i.next();
    239         while (i.hasNext()) {
    240             T t = i.next();
    241             assertTrue(comp.compare(last, t) <= 0);
    242             assertTrue(comp.compare(t, last) >= 0);
    243             last = t;
    244         }
    245     }
    246 
    247     public static<T extends Comparable<? super T>> void assertSorted(Iterable<T> iter) {
    248         assertSorted(iter.iterator());
    249     }
    250 
    251     public static<T> void assertSorted(Iterable<T> iter, Comparator<? super T> comp) {
    252         assertSorted(iter.iterator(), comp);
    253     }
    254 
    255     public static <T> void assertUnique(Iterable<T> iter) {
    256         assertUnique(iter.iterator());
    257     }
    258 
    259     public static<T> void assertUnique(Iterator<T> iter) {
    260         if (!iter.hasNext()) {
    261             return;
    262         }
    263 
    264         if (iter instanceof PrimitiveIterator.OfInt
    265             || iter instanceof PrimitiveIterator.OfDouble
    266             || iter instanceof PrimitiveIterator.OfLong) {
    267             iter = toBoxedList(iter).iterator();
    268         }
    269 
    270         Set<T> uniq = new HashSet<>();
    271         while(iter.hasNext()) {
    272             T each = iter.next();
    273             assertTrue(!uniq.contains(each), "Not unique");
    274             uniq.add(each);
    275         }
    276     }
    277 
    278     public static<T> void assertContents(Iterable<T> actual, Iterable<T> expected) {
    279         if (actual instanceof Collection && expected instanceof Collection) {
    280             assertEquals(actual, expected);
    281         } else {
    282             assertContents(actual.iterator(), expected.iterator());
    283         }
    284     }
    285 
    286     public static<T> void assertContents(Iterator<T> actual, Iterator<T> expected) {
    287         assertEquals(toBoxedList(actual), toBoxedList(expected));
    288     }
    289 
    290     @SafeVarargs
    291     @SuppressWarnings("varargs")
    292     public static<T> void assertContents(Iterator<T> actual, T... expected) {
    293         assertContents(actual, Arrays.asList(expected).iterator());
    294     }
    295 
    296     /**
    297      * The all consuming consumer (rampant capitalist) that can accepting a reference or any primitive value.
    298      */
    299     private static interface OmnivorousConsumer<T>
    300             extends Consumer<T>, IntConsumer, LongConsumer, DoubleConsumer { }
    301 
    302     @SuppressWarnings({"rawtypes", "unchecked"})
    303     public static<T> Consumer<T> toBoxingConsumer(Consumer<? super T> c) {
    304         return (Consumer<T>) new OmnivorousConsumer() {
    305             @Override
    306             public void accept(Object t) {
    307                 c.accept((T) t);
    308             }
    309 
    310             @Override
    311             public void accept(int t) {
    312                 accept((Object) t);
    313             }
    314 
    315             @Override
    316             public void accept(long t) {
    317                 accept((Object) t);
    318             }
    319 
    320             @Override
    321             public void accept(double t) {
    322                 accept((Object) t);
    323             }
    324         };
    325     }
    326 
    327     /**
    328      * Convert an iterator to a list using forEach with an implementation of
    329      * {@link java.util.stream.LambdaTestHelpers.OmnivorousConsumer}.
    330      *
    331      * This ensures equality comparisons for test results do not trip
    332      * the boxing trip-wires.
    333      */
    334     private static<T> List<T> toBoxedList(Iterator<T> it) {
    335         List<T> l = new ArrayList<>();
    336         it.forEachRemaining(toBoxingConsumer(l::add));
    337         return l;
    338     }
    339 
    340     /**
    341      * Convert a spliterator to a list using forEach with an implementation of
    342      * {@link java.util.stream.LambdaTestHelpers.OmnivorousConsumer}.
    343      *
    344      * This ensures equality comparisons for test results do not trip
    345      * the boxing trip-wires.
    346      */
    347     public static<T> List<T> toBoxedList(Spliterator<T> sp) {
    348         List<T> l = new ArrayList<>();
    349         sp.forEachRemaining(toBoxingConsumer(l::add));
    350         return l;
    351     }
    352 
    353     /**
    354      * Convert an iterator to a multi-set, represented as a Map, using forEach with an implementation of
    355      * {@link java.util.stream.LambdaTestHelpers.OmnivorousConsumer}.
    356      *
    357      * This ensures equality comparisons for test results do not trip
    358      * the boxing trip-wires.
    359      */
    360     @SuppressWarnings("unchecked")
    361     private static<T> Map<T, Integer> toBoxedMultiset(Iterator<T> it) {
    362         Map<Object, Integer> result = new HashMap<>();
    363 
    364         it.forEachRemaining(toBoxingConsumer(o -> {
    365                 if (result.containsKey(o))
    366                     result.put(o, result.get(o) + 1);
    367                 else
    368                     result.put(o, 1);
    369             }));
    370 
    371         return (Map<T, Integer>) result;
    372     }
    373 
    374     @SuppressWarnings("unchecked")
    375     public static<T> Map<T, Integer> toBoxedMultiset(Spliterator<T> it) {
    376         Map<Object, Integer> result = new HashMap<>();
    377 
    378         it.forEachRemaining(toBoxingConsumer(o -> {
    379                 if (result.containsKey(o))
    380                     result.put(o, result.get(o) + 1);
    381                 else
    382                     result.put(o, 1);
    383             }));
    384 
    385         return (Map<T, Integer>) result;
    386     }
    387 
    388     @SuppressWarnings("unchecked")
    389     public static void assertContentsEqual(Object a, Object b) {
    390         if (a instanceof Iterable && b instanceof Iterable)
    391             assertContents((Iterable) a, (Iterable) b);
    392         else
    393             assertEquals(a, b);
    394     }
    395 
    396     public static<T> void assertContentsUnordered(Iterable<T> actual, Iterable<T> expected) {
    397         assertContentsUnordered(actual.iterator(), expected.iterator());
    398     }
    399 
    400     public static<T> void assertContentsUnordered(Iterator<T> actual, Iterator<T> expected) {
    401         assertEquals(toBoxedMultiset(actual), toBoxedMultiset(expected));
    402     }
    403 
    404     public static void launderAssertion(Runnable r, Supplier<String> additionalInfo) {
    405         try {
    406             r.run();
    407         }
    408         catch (AssertionError ae) {
    409             AssertionError cloned = new AssertionError(ae.getMessage() + String.format("%n%s", additionalInfo.get()));
    410             cloned.setStackTrace(ae.getStackTrace());
    411             if (ae.getCause() != null)
    412                 cloned.initCause(ae.getCause());
    413             throw cloned;
    414         }
    415     }
    416 
    417     public static <T, S extends BaseStream<T, S>>
    418     List<Function<S, S>> permuteStreamFunctions(List<Function<S, S>> opFunctions) {
    419         List<List<Function<S, S>>> opFunctionPermutations = perm(opFunctions);
    420 
    421         List<Function<S, S>> appliedFunctions = new ArrayList<>();
    422         for (List<Function<S, S>> fs : opFunctionPermutations) {
    423             Function<S, S> applied = s -> {
    424                 for (Function<S, S> f : fs) {
    425                     s = f.apply(s);
    426                 }
    427                 return s;
    428             };
    429             appliedFunctions.add(applied);
    430         }
    431 
    432         return appliedFunctions;
    433     }
    434 
    435     private static <T> List<T> sub(List<T> l, int index) {
    436         List<T> subL = new ArrayList<>(l);
    437         subL.remove(index);
    438         return subL;
    439     }
    440 
    441     public static <T> List<List<T>> perm(List<T> l) {
    442         List<List<T>> result = new ArrayList<>();
    443         for (int i = 0; i < l.size(); i++) {
    444             for (List<T> perm : perm(sub(l, i))) {
    445                 perm.add(0, l.get(i));
    446                 result.add(perm);
    447             }
    448         }
    449         result.add(new ArrayList<T>());
    450 
    451         return result;
    452     }
    453 
    454     public static String flagsToString(int flags) {
    455         StringJoiner sj = new StringJoiner(", ", "StreamOpFlag[", "]");
    456         if (StreamOpFlag.DISTINCT.isKnown(flags)) sj.add("IS_DISTINCT");
    457         if (StreamOpFlag.ORDERED.isKnown(flags)) sj.add("IS_ORDERED");
    458         if (StreamOpFlag.SIZED.isKnown(flags)) sj.add("IS_SIZED");
    459         if (StreamOpFlag.SORTED.isKnown(flags)) sj.add("IS_SORTED");
    460         if (StreamOpFlag.SHORT_CIRCUIT.isKnown(flags)) sj.add("IS_SHORT_CIRCUIT");
    461         return sj.toString();
    462     }
    463 }
    464