提交 1b299b33 编写于 作者: P psandoz

8016455: Sync stream tests from lambda to tl

Reviewed-by: mduigou
Contributed-by: NBrian Goetz &lt;brian.goetz@oracle.com&gt;, Paul Sandoz <paul.sandoz@oracle.com>
上级 ffb64db0
...@@ -129,7 +129,6 @@ public class IntStreamTestDataProvider { ...@@ -129,7 +129,6 @@ public class IntStreamTestDataProvider {
() -> IntStream.range(0, ints.length).spliterator())); () -> IntStream.range(0, ints.length).spliterator()));
spliterators.add(splitDescr("IntStream.intRangeClosed(0,l):" + name, spliterators.add(splitDescr("IntStream.intRangeClosed(0,l):" + name,
() -> IntStream.rangeClosed(0, ints.length).spliterator())); () -> IntStream.rangeClosed(0, ints.length).spliterator()));
// Need more! // Need more!
} }
spliteratorTestData = spliterators.toArray(new Object[0][]); spliteratorTestData = spliterators.toArray(new Object[0][]);
......
...@@ -269,7 +269,7 @@ public class LambdaTestHelpers { ...@@ -269,7 +269,7 @@ public class LambdaTestHelpers {
Set<T> uniq = new HashSet<>(); Set<T> uniq = new HashSet<>();
while(iter.hasNext()) { while(iter.hasNext()) {
T each = iter.next(); T each = iter.next();
assertTrue(!uniq.contains(each)); assertTrue(!uniq.contains(each), "Not unique");
uniq.add(each); uniq.add(each);
} }
} }
......
/*
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*
* This code is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* version 2 for more details (a copy is included in the LICENSE file that
* accompanied this code).
*
* You should have received a copy of the GNU General Public License version
* 2 along with this work; if not, write to the Free Software Foundation,
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
*
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
* or visit www.oracle.com if you need additional information or have any
* questions.
*/
package java.util.stream;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import org.testng.Assert;
import org.testng.ITestResult;
import org.testng.annotations.AfterMethod;
import org.testng.annotations.BeforeMethod;
import org.testng.annotations.Test;
/**
* LoggingTestCase
*
*/
@Test
public class LoggingTestCase extends Assert {
private Map<String, Object> context = new HashMap<>();
@BeforeMethod
public void before() {
context.clear();
}
@AfterMethod
public void after(ITestResult result) {
if (!result.isSuccess()) {
List<Object> list = new ArrayList<>();
Collections.addAll(list, result.getParameters());
list.add(context.toString());
result.setParameters(list.toArray(new Object[list.size()]));
}
}
protected void setContext(String key, Object value) {
context.put(key, value);
}
protected void clearContext(String key) {
context.remove(key);
}
}
...@@ -50,7 +50,7 @@ import org.testng.annotations.Test; ...@@ -50,7 +50,7 @@ import org.testng.annotations.Test;
* ways and asserts that they produce equivalent results. * ways and asserts that they produce equivalent results.
*/ */
@Test @Test
public abstract class OpTestCase extends Assert { public abstract class OpTestCase extends LoggingTestCase {
private final Map<StreamShape, Set<? extends BaseStreamTestScenario>> testScenarios; private final Map<StreamShape, Set<? extends BaseStreamTestScenario>> testScenarios;
...@@ -67,6 +67,25 @@ public abstract class OpTestCase extends Assert { ...@@ -67,6 +67,25 @@ public abstract class OpTestCase extends Assert {
return ((AbstractPipeline) s).getStreamFlags(); return ((AbstractPipeline) s).getStreamFlags();
} }
/**
* An asserter for results produced when exercising of stream or terminal
* tests.
*
* @param <R> the type of result to assert on
*/
public interface ResultAsserter<R> {
/**
* Assert a result produced when exercising of stream or terminal
* test.
*
* @param actual the actual result
* @param excepted the expected result
* @param isOrdered true if the pipeline is ordered
* @param isParallel true if the pipeline is parallel
*/
void assertResult(R actual, R excepted, boolean isOrdered, boolean isParallel);
}
// Exercise stream operations // Exercise stream operations
public interface BaseStreamTestScenario { public interface BaseStreamTestScenario {
...@@ -190,14 +209,19 @@ public abstract class OpTestCase extends Assert { ...@@ -190,14 +209,19 @@ public abstract class OpTestCase extends Assert {
Set<BaseStreamTestScenario> testSet = new HashSet<>(); Set<BaseStreamTestScenario> testSet = new HashSet<>();
Collection<U> refResult; Collection<U> refResult;
boolean isOrdered;
Consumer<TestData<T, S_IN>> before = LambdaTestHelpers.bEmpty; Consumer<TestData<T, S_IN>> before = LambdaTestHelpers.bEmpty;
Consumer<TestData<T, S_IN>> after = LambdaTestHelpers.bEmpty; Consumer<TestData<T, S_IN>> after = LambdaTestHelpers.bEmpty;
BiConsumer<Iterable<U>, Iterable<U>> sequentialEqualityAsserter = LambdaTestHelpers::assertContentsEqual; ResultAsserter<Iterable<U>> resultAsserter = (act, exp, ord, par) -> {
BiConsumer<Iterable<U>, Iterable<U>> parallelEqualityAsserter = LambdaTestHelpers::assertContentsEqual; if (par & !ord) {
LambdaTestHelpers.assertContentsUnordered(act, exp);
}
else {
LambdaTestHelpers.assertContentsEqual(act, exp);
}
};
private ExerciseDataStreamBuilder(TestData<T, S_IN> data, Function<S_IN, S_OUT> m) { private ExerciseDataStreamBuilder(TestData<T, S_IN> data, Function<S_IN, S_OUT> m) {
this.data = data; this.data = data;
...@@ -211,10 +235,6 @@ public abstract class OpTestCase extends Assert { ...@@ -211,10 +235,6 @@ public abstract class OpTestCase extends Assert {
testSet.addAll(testScenarios.get(shape)); testSet.addAll(testScenarios.get(shape));
} }
public BiConsumer<Iterable<U>, Iterable<U>> getEqualityAsserter(BaseStreamTestScenario t) {
return t.isParallel() ? parallelEqualityAsserter : sequentialEqualityAsserter;
}
// //
public <I extends Iterable<U>> ExerciseDataStreamBuilder<T, U, S_IN, S_OUT> expectedResult(I expectedResult) { public <I extends Iterable<U>> ExerciseDataStreamBuilder<T, U, S_IN, S_OUT> expectedResult(I expectedResult) {
...@@ -299,29 +319,15 @@ public abstract class OpTestCase extends Assert { ...@@ -299,29 +319,15 @@ public abstract class OpTestCase extends Assert {
return this; return this;
} }
public ExerciseDataStreamBuilder<T, U, S_IN, S_OUT> sequentialEqualityAsserter(BiConsumer<Iterable<U>, Iterable<U>> equalator) { public ExerciseDataStreamBuilder<T, U, S_IN, S_OUT> resultAsserter(ResultAsserter<Iterable<U>> resultAsserter) {
this.sequentialEqualityAsserter = equalator; this.resultAsserter = resultAsserter;
return this;
}
public ExerciseDataStreamBuilder<T, U, S_IN, S_OUT> parallelEqualityAsserter(BiConsumer<Iterable<U>, Iterable<U>> equalator) {
this.parallelEqualityAsserter = equalator;
return this; return this;
} }
// Build method // Build method
private long count(StreamShape shape, BaseStream s) {
switch (shape) {
case REFERENCE: return ((Stream) s).count();
case INT_VALUE: return ((IntStream) s).count();
case LONG_VALUE: return ((LongStream) s).count();
case DOUBLE_VALUE: return ((DoubleStream) s).count();
default: throw new IllegalStateException("Unknown shape: " + shape);
}
}
public Collection<U> exercise() { public Collection<U> exercise() {
final boolean isOrdered;
if (refResult == null) { if (refResult == null) {
// Induce the reference result // Induce the reference result
before.accept(data); before.accept(data);
...@@ -330,9 +336,10 @@ public abstract class OpTestCase extends Assert { ...@@ -330,9 +336,10 @@ public abstract class OpTestCase extends Assert {
Node<U> refNodeResult = ((AbstractPipeline<?, U, ?>) sOut).evaluateToArrayNode(size -> (U[]) new Object[size]); Node<U> refNodeResult = ((AbstractPipeline<?, U, ?>) sOut).evaluateToArrayNode(size -> (U[]) new Object[size]);
refResult = LambdaTestHelpers.toBoxedList(refNodeResult.spliterator()); refResult = LambdaTestHelpers.toBoxedList(refNodeResult.spliterator());
after.accept(data); after.accept(data);
S_OUT anotherCopy = m.apply(data.stream()); }
long count = count(((AbstractPipeline) anotherCopy).getOutputShape(), anotherCopy); else {
assertEquals(count, refNodeResult.count()); S_OUT sOut = m.apply(data.stream());
isOrdered = StreamOpFlag.ORDERED.isKnown(((AbstractPipeline) sOut).getStreamFlags());
} }
List<Error> errors = new ArrayList<>(); List<Error> errors = new ArrayList<>();
...@@ -343,16 +350,20 @@ public abstract class OpTestCase extends Assert { ...@@ -343,16 +350,20 @@ public abstract class OpTestCase extends Assert {
List<U> result = new ArrayList<>(); List<U> result = new ArrayList<>();
test.run(data, LambdaTestHelpers.<U>toBoxingConsumer(result::add), m); test.run(data, LambdaTestHelpers.<U>toBoxingConsumer(result::add), m);
Runnable asserter = () -> getEqualityAsserter(test).accept(result, refResult); Runnable asserter = () -> resultAsserter.assertResult(result, refResult, isOrdered, test.isParallel());
if (test.isParallel() && !isOrdered)
asserter = () -> LambdaTestHelpers.assertContentsUnordered(result, refResult); if (refResult.size() > 1000) {
LambdaTestHelpers.launderAssertion( LambdaTestHelpers.launderAssertion(
asserter, asserter,
() -> String.format("%n%s: %s != %s", test, refResult, result)); () -> String.format("%n%s: [actual size=%d] != [expected size=%d]", test, result.size(), refResult.size()));
}
else {
LambdaTestHelpers.launderAssertion(
asserter,
() -> String.format("%n%s: [actual] %s != [expected] %s", test, result, refResult));
}
after.accept(data); after.accept(data);
// } catch (AssertionError ae) {
// errors.add(ae);
} catch (Throwable t) { } catch (Throwable t) {
errors.add(new Error(String.format("%s: %s", test, t), t)); errors.add(new Error(String.format("%s: %s", test, t), t));
} }
...@@ -406,8 +417,7 @@ public abstract class OpTestCase extends Assert { ...@@ -406,8 +417,7 @@ public abstract class OpTestCase extends Assert {
Set<TerminalTestScenario> testSet = EnumSet.allOf(TerminalTestScenario.class); Set<TerminalTestScenario> testSet = EnumSet.allOf(TerminalTestScenario.class);
Function<S_OUT, BiConsumer<R, R>> sequentialEqualityAsserter = s -> LambdaTestHelpers::assertContentsEqual; ResultAsserter<R> resultAsserter = (act, exp, ord, par) -> LambdaTestHelpers.assertContentsEqual(act, exp);
Function<S_OUT, BiConsumer<R, R>> parallelEqualityAsserter = s -> LambdaTestHelpers::assertContentsEqual;
private ExerciseDataTerminalBuilder(TestData<T, S_IN> data, Function<S_IN, S_OUT> streamF, Function<S_OUT, R> terminalF) { private ExerciseDataTerminalBuilder(TestData<T, S_IN> data, Function<S_IN, S_OUT> streamF, Function<S_OUT, R> terminalF) {
this.data = data; this.data = data;
...@@ -423,23 +433,12 @@ public abstract class OpTestCase extends Assert { ...@@ -423,23 +433,12 @@ public abstract class OpTestCase extends Assert {
} }
public ExerciseDataTerminalBuilder<T, U, R, S_IN, S_OUT> equalator(BiConsumer<R, R> equalityAsserter) { public ExerciseDataTerminalBuilder<T, U, R, S_IN, S_OUT> equalator(BiConsumer<R, R> equalityAsserter) {
this.sequentialEqualityAsserter = s -> equalityAsserter; resultAsserter = (act, exp, ord, par) -> equalityAsserter.accept(act, exp);
this.parallelEqualityAsserter = s -> equalityAsserter;
return this;
}
public ExerciseDataTerminalBuilder<T, U, R, S_IN, S_OUT> sequentialEqualityAsserter(BiConsumer<R, R> equalityAsserter) {
this.sequentialEqualityAsserter = s -> equalityAsserter;
return this;
}
public ExerciseDataTerminalBuilder<T, U, R, S_IN, S_OUT> parallelEqualityAsserter(BiConsumer<R, R> equalityAsserter) {
this.parallelEqualityAsserter = s -> equalityAsserter;
return this; return this;
} }
public ExerciseDataTerminalBuilder<T, U, R, S_IN, S_OUT> parallelEqualityAsserter(Function<S_OUT, BiConsumer<R, R>> equalatorProvider) { public ExerciseDataTerminalBuilder<T, U, R, S_IN, S_OUT> resultAsserter(ResultAsserter<R> resultAsserter) {
this.parallelEqualityAsserter = equalatorProvider; this.resultAsserter = resultAsserter;
return this; return this;
} }
...@@ -467,8 +466,9 @@ public abstract class OpTestCase extends Assert { ...@@ -467,8 +466,9 @@ public abstract class OpTestCase extends Assert {
// Build method // Build method
public R exercise() { public R exercise() {
S_OUT out = streamF.apply(data.stream()); S_OUT out = streamF.apply(data.stream()).sequential();
AbstractPipeline ap = (AbstractPipeline) out; AbstractPipeline ap = (AbstractPipeline) out;
boolean isOrdered = StreamOpFlag.ORDERED.isKnown(ap.getStreamFlags());
StreamShape shape = ap.getOutputShape(); StreamShape shape = ap.getOutputShape();
Node<U> node = ap.evaluateToArrayNode(size -> (U[]) new Object[size]); Node<U> node = ap.evaluateToArrayNode(size -> (U[]) new Object[size]);
...@@ -481,9 +481,8 @@ public abstract class OpTestCase extends Assert { ...@@ -481,9 +481,8 @@ public abstract class OpTestCase extends Assert {
S_OUT source = (S_OUT) createPipeline(shape, node.spliterator(), S_OUT source = (S_OUT) createPipeline(shape, node.spliterator(),
StreamOpFlag.IS_ORDERED | StreamOpFlag.IS_SIZED, StreamOpFlag.IS_ORDERED | StreamOpFlag.IS_SIZED,
false); false);
BiConsumer<R, R> asserter = sequentialEqualityAsserter.apply(source);
R result = terminalF.apply(source); R result = terminalF.apply(source);
LambdaTestHelpers.launderAssertion(() -> asserter.accept(refResult, result), LambdaTestHelpers.launderAssertion(() -> resultAsserter.assertResult(result, refResult, isOrdered, false),
() -> String.format("Single sequential: %s != %s", refResult, result)); () -> String.format("Single sequential: %s != %s", refResult, result));
} }
...@@ -491,11 +490,10 @@ public abstract class OpTestCase extends Assert { ...@@ -491,11 +490,10 @@ public abstract class OpTestCase extends Assert {
S_OUT source = (S_OUT) createPipeline(shape, node.spliterator(), S_OUT source = (S_OUT) createPipeline(shape, node.spliterator(),
StreamOpFlag.IS_ORDERED | StreamOpFlag.IS_SIZED, StreamOpFlag.IS_ORDERED | StreamOpFlag.IS_SIZED,
false); false);
// Force short-curcuit // Force short-circuit
source = (S_OUT) chain(source, new ShortCircuitOp<U>(shape)); source = (S_OUT) chain(source, new ShortCircuitOp<U>(shape));
BiConsumer<R, R> asserter = sequentialEqualityAsserter.apply(source);
R result = terminalF.apply(source); R result = terminalF.apply(source);
LambdaTestHelpers.launderAssertion(() -> asserter.accept(refResult, result), LambdaTestHelpers.launderAssertion(() -> resultAsserter.assertResult(result, refResult, isOrdered, false),
() -> String.format("Single sequential pull: %s != %s", refResult, result)); () -> String.format("Single sequential pull: %s != %s", refResult, result));
} }
...@@ -503,44 +501,39 @@ public abstract class OpTestCase extends Assert { ...@@ -503,44 +501,39 @@ public abstract class OpTestCase extends Assert {
S_OUT source = (S_OUT) createPipeline(shape, node.spliterator(), S_OUT source = (S_OUT) createPipeline(shape, node.spliterator(),
StreamOpFlag.IS_ORDERED | StreamOpFlag.IS_SIZED, StreamOpFlag.IS_ORDERED | StreamOpFlag.IS_SIZED,
true); true);
BiConsumer<R, R> asserter = parallelEqualityAsserter.apply(source);
R result = terminalF.apply(source); R result = terminalF.apply(source);
LambdaTestHelpers.launderAssertion(() -> asserter.accept(refResult, result), LambdaTestHelpers.launderAssertion(() -> resultAsserter.assertResult(result, refResult, isOrdered, true),
() -> String.format("Single parallel: %s != %s", refResult, result)); () -> String.format("Single parallel: %s != %s", refResult, result));
} }
if (testSet.contains(TerminalTestScenario.ALL_SEQUENTIAL)) { if (testSet.contains(TerminalTestScenario.ALL_SEQUENTIAL)) {
// This may forEach or tryAdvance depending on the terminal op implementation // This may forEach or tryAdvance depending on the terminal op implementation
S_OUT source = streamF.apply(data.stream()); S_OUT source = streamF.apply(data.stream());
BiConsumer<R, R> asserter = sequentialEqualityAsserter.apply(source);
R result = terminalF.apply(source); R result = terminalF.apply(source);
LambdaTestHelpers.launderAssertion(() -> asserter.accept(refResult, result), LambdaTestHelpers.launderAssertion(() -> resultAsserter.assertResult(result, refResult, isOrdered, false),
() -> String.format("All sequential: %s != %s", refResult, result)); () -> String.format("All sequential: %s != %s", refResult, result));
} }
if (testSet.contains(TerminalTestScenario.ALL_SEQUENTIAL_SHORT_CIRCUIT)) { if (testSet.contains(TerminalTestScenario.ALL_SEQUENTIAL_SHORT_CIRCUIT)) {
S_OUT source = streamF.apply(data.stream()); S_OUT source = streamF.apply(data.stream());
// Force short-curcuit // Force short-circuit
source = (S_OUT) chain(source, new ShortCircuitOp<U>(shape)); source = (S_OUT) chain(source, new ShortCircuitOp<U>(shape));
BiConsumer<R, R> asserter = sequentialEqualityAsserter.apply(source);
R result = terminalF.apply(source); R result = terminalF.apply(source);
LambdaTestHelpers.launderAssertion(() -> asserter.accept(refResult, result), LambdaTestHelpers.launderAssertion(() -> resultAsserter.assertResult(result, refResult, isOrdered, false),
() -> String.format("All sequential pull: %s != %s", refResult, result)); () -> String.format("All sequential pull: %s != %s", refResult, result));
} }
if (testSet.contains(TerminalTestScenario.ALL_PARALLEL)) { if (testSet.contains(TerminalTestScenario.ALL_PARALLEL)) {
S_OUT source = streamF.apply(data.parallelStream()); S_OUT source = streamF.apply(data.parallelStream());
BiConsumer<R, R> asserter = parallelEqualityAsserter.apply(source);
R result = terminalF.apply(source); R result = terminalF.apply(source);
LambdaTestHelpers.launderAssertion(() -> asserter.accept(refResult, result), LambdaTestHelpers.launderAssertion(() -> resultAsserter.assertResult(result, refResult, isOrdered, true),
() -> String.format("All parallel: %s != %s", refResult, result)); () -> String.format("All parallel: %s != %s", refResult, result));
} }
if (testSet.contains(TerminalTestScenario.ALL_PARALLEL_SEQUENTIAL)) { if (testSet.contains(TerminalTestScenario.ALL_PARALLEL_SEQUENTIAL)) {
S_OUT source = streamF.apply(data.parallelStream()); S_OUT source = streamF.apply(data.parallelStream());
BiConsumer<R, R> asserter = parallelEqualityAsserter.apply(source);
R result = terminalF.apply(source.sequential()); R result = terminalF.apply(source.sequential());
LambdaTestHelpers.launderAssertion(() -> asserter.accept(refResult, result), LambdaTestHelpers.launderAssertion(() -> resultAsserter.assertResult(result, refResult, isOrdered, false),
() -> String.format("All parallel then sequential: %s != %s", refResult, result)); () -> String.format("All parallel then sequential: %s != %s", refResult, result));
} }
......
...@@ -65,7 +65,7 @@ public class SpliteratorTestHelper { ...@@ -65,7 +65,7 @@ public class SpliteratorTestHelper {
} }
} }
testSpliterator(supplier, c -> new BoxingAdapter(c)); testSpliterator(supplier, BoxingAdapter::new);
} }
public static void testLongSpliterator(Supplier<Spliterator.OfLong> supplier) { public static void testLongSpliterator(Supplier<Spliterator.OfLong> supplier) {
...@@ -87,7 +87,7 @@ public class SpliteratorTestHelper { ...@@ -87,7 +87,7 @@ public class SpliteratorTestHelper {
} }
} }
testSpliterator(supplier, c -> new BoxingAdapter(c)); testSpliterator(supplier, BoxingAdapter::new);
} }
public static void testDoubleSpliterator(Supplier<Spliterator.OfDouble> supplier) { public static void testDoubleSpliterator(Supplier<Spliterator.OfDouble> supplier) {
...@@ -109,7 +109,7 @@ public class SpliteratorTestHelper { ...@@ -109,7 +109,7 @@ public class SpliteratorTestHelper {
} }
} }
testSpliterator(supplier, c -> new BoxingAdapter(c)); testSpliterator(supplier, BoxingAdapter::new);
} }
static <T, S extends Spliterator<T>> void testSpliterator(Supplier<S> supplier, static <T, S extends Spliterator<T>> void testSpliterator(Supplier<S> supplier,
......
...@@ -162,4 +162,18 @@ public class DoubleNodeTest extends OpTestCase { ...@@ -162,4 +162,18 @@ public class DoubleNodeTest extends OpTestCase {
public void testSpliterator(double[] array, Node.OfDouble n) { public void testSpliterator(double[] array, Node.OfDouble n) {
SpliteratorTestHelper.testDoubleSpliterator(n::spliterator); SpliteratorTestHelper.testDoubleSpliterator(n::spliterator);
} }
@Test(dataProvider = "nodes")
public void testTruncate(double[] array, Node.OfDouble n) {
int[] nums = new int[] { 0, 1, array.length / 2, array.length - 1, array.length };
for (int start : nums)
for (int end : nums) {
if (start < 0 || end < 0 || end < start || end > array.length)
continue;
Node.OfDouble slice = n.truncate(start, end, Double[]::new);
double[] asArray = slice.asPrimitiveArray();
for (int k = start; k < end; k++)
assertEquals(array[k], asArray[k - start]);
}
}
} }
...@@ -160,4 +160,18 @@ public class IntNodeTest extends OpTestCase { ...@@ -160,4 +160,18 @@ public class IntNodeTest extends OpTestCase {
public void testSpliterator(int[] array, Node.OfInt n) { public void testSpliterator(int[] array, Node.OfInt n) {
SpliteratorTestHelper.testIntSpliterator(n::spliterator); SpliteratorTestHelper.testIntSpliterator(n::spliterator);
} }
@Test(dataProvider = "nodes")
public void testTruncate(int[] array, Node.OfInt n) {
int[] nums = new int[] { 0, 1, array.length / 2, array.length - 1, array.length };
for (int start : nums)
for (int end : nums) {
if (start < 0 || end < 0 || end < start || end > array.length)
continue;
Node.OfInt slice = n.truncate(start, end, Integer[]::new);
int[] asArray = slice.asPrimitiveArray();
for (int k = start; k < end; k++)
assertEquals(array[k], asArray[k - start]);
}
}
} }
...@@ -161,4 +161,18 @@ public class LongNodeTest extends OpTestCase { ...@@ -161,4 +161,18 @@ public class LongNodeTest extends OpTestCase {
public void testSpliterator(long[] array, Node.OfLong n) { public void testSpliterator(long[] array, Node.OfLong n) {
SpliteratorTestHelper.testLongSpliterator(n::spliterator); SpliteratorTestHelper.testLongSpliterator(n::spliterator);
} }
@Test(dataProvider = "nodes")
public void testTruncate(long[] array, Node.OfLong n) {
int[] nums = new int[] { 0, 1, array.length / 2, array.length - 1, array.length };
for (int start : nums)
for (int end : nums) {
if (start < 0 || end < 0 || end < start || end > array.length)
continue;
Node.OfLong slice = n.truncate(start, end, Long[]::new);
long[] asArray = slice.asPrimitiveArray();
for (int k = start; k < end; k++)
assertEquals(array[k], asArray[k - start]);
}
}
} }
...@@ -137,4 +137,18 @@ public class NodeTest extends OpTestCase { ...@@ -137,4 +137,18 @@ public class NodeTest extends OpTestCase {
public void testSpliterator(Integer[] array, Node<Integer> n) { public void testSpliterator(Integer[] array, Node<Integer> n) {
SpliteratorTestHelper.testSpliterator(n::spliterator); SpliteratorTestHelper.testSpliterator(n::spliterator);
} }
@Test(dataProvider = "nodes")
public void testTruncate(Integer[] array, Node<Integer> n) {
int[] nums = new int[] { 0, 1, array.length / 2, array.length - 1, array.length };
for (int start : nums)
for (int end : nums) {
if (start < 0 || end < 0 || end < start || end > array.length)
continue;
Node<Integer> slice = n.truncate(start, end, Integer[]::new);
Integer[] asArray = slice.asArray(Integer[]::new);
for (int k = start; k < end; k++)
assertEquals(array[k], asArray[k - start]);
}
}
} }
...@@ -184,7 +184,6 @@ public class UnorderedTest extends OpTestCase { ...@@ -184,7 +184,6 @@ public class UnorderedTest extends OpTestCase {
UnaryOperator<S> fi = interpose(f, (S s) -> (S) chain(s, checkClearOrderedOp)); UnaryOperator<S> fi = interpose(f, (S s) -> (S) chain(s, checkClearOrderedOp));
withData(data). withData(data).
terminal(fi, terminalF). terminal(fi, terminalF).
without(TerminalTestScenario.ALL_PARALLEL_SEQUENTIAL).
equalator(equalityAsserter). equalator(equalityAsserter).
exercise(); exercise();
} }
...@@ -195,7 +194,6 @@ public class UnorderedTest extends OpTestCase { ...@@ -195,7 +194,6 @@ public class UnorderedTest extends OpTestCase {
UnaryOperator<S> fi = interpose(f, (S s) -> (S) chain(s, checkSetOrderedOp)); UnaryOperator<S> fi = interpose(f, (S s) -> (S) chain(s, checkSetOrderedOp));
withData(data). withData(data).
terminal(fi, s -> terminalF.apply(s.sequential())). terminal(fi, s -> terminalF.apply(s.sequential())).
without(TerminalTestScenario.ALL_PARALLEL_SEQUENTIAL).
equalator(equalityAsserter). equalator(equalityAsserter).
exercise(); exercise();
} }
......
...@@ -64,7 +64,6 @@ public class DistinctOpTest extends OpTestCase { ...@@ -64,7 +64,6 @@ public class DistinctOpTest extends OpTestCase {
node = withData(data). node = withData(data).
stream(s -> s.unordered().distinct()). stream(s -> s.unordered().distinct()).
parallelEqualityAsserter(LambdaTestHelpers::assertContentsUnordered).
exercise(); exercise();
assertUnique(node); assertUnique(node);
......
...@@ -58,6 +58,17 @@ public class ForEachOpTest extends OpTestCase { ...@@ -58,6 +58,17 @@ public class ForEachOpTest extends OpTestCase {
55); 55);
} }
private <U> ResultAsserter<List<U>> resultAsserter() {
return (act, exp, ord, par) -> {
if (par) {
LambdaTestHelpers.assertContentsUnordered(act, exp);
}
else {
LambdaTestHelpers.assertContents(act, exp);
}
};
}
@Test @Test
public void testForEachOrdered() { public void testForEachOrdered() {
List<Integer> input = countTo(10000); List<Integer> input = countTo(10000);
...@@ -93,13 +104,13 @@ public class ForEachOpTest extends OpTestCase { ...@@ -93,13 +104,13 @@ public class ForEachOpTest extends OpTestCase {
// Test head // Test head
withData(data). withData(data).
terminal(terminalFunc). terminal(terminalFunc).
parallelEqualityAsserter(LambdaTestHelpers::assertContentsUnordered). resultAsserter(resultAsserter()).
exercise(); exercise();
// Test multiple stages // Test multiple stages
withData(data). withData(data).
terminal(s -> s.map(LambdaTestHelpers.identity()), terminalFunc). terminal(s -> s.map(LambdaTestHelpers.identity()), terminalFunc).
parallelEqualityAsserter(LambdaTestHelpers::assertContentsUnordered). resultAsserter(resultAsserter()).
exercise(); exercise();
} }
...@@ -141,13 +152,13 @@ public class ForEachOpTest extends OpTestCase { ...@@ -141,13 +152,13 @@ public class ForEachOpTest extends OpTestCase {
// Test head // Test head
withData(data). withData(data).
terminal(terminalFunc). terminal(terminalFunc).
parallelEqualityAsserter(LambdaTestHelpers::assertContentsUnordered). resultAsserter(resultAsserter()).
exercise(); exercise();
// Test multiple stages // Test multiple stages
withData(data). withData(data).
terminal(s -> s.map(i -> i), terminalFunc). terminal(s -> s.map(i -> i), terminalFunc).
parallelEqualityAsserter(LambdaTestHelpers::assertContentsUnordered). resultAsserter(resultAsserter()).
exercise(); exercise();
} }
...@@ -189,13 +200,13 @@ public class ForEachOpTest extends OpTestCase { ...@@ -189,13 +200,13 @@ public class ForEachOpTest extends OpTestCase {
// Test head // Test head
withData(data). withData(data).
terminal(terminalFunc). terminal(terminalFunc).
parallelEqualityAsserter(LambdaTestHelpers::assertContentsUnordered). resultAsserter(resultAsserter()).
exercise(); exercise();
// Test multiple stages // Test multiple stages
withData(data). withData(data).
terminal(s -> s.map(i -> i), terminalFunc). terminal(s -> s.map(i -> i), terminalFunc).
parallelEqualityAsserter(LambdaTestHelpers::assertContentsUnordered). resultAsserter(resultAsserter()).
exercise(); exercise();
} }
...@@ -237,13 +248,13 @@ public class ForEachOpTest extends OpTestCase { ...@@ -237,13 +248,13 @@ public class ForEachOpTest extends OpTestCase {
// Test head // Test head
withData(data). withData(data).
terminal(terminalFunc). terminal(terminalFunc).
parallelEqualityAsserter(LambdaTestHelpers::assertContentsUnordered). resultAsserter(resultAsserter()).
exercise(); exercise();
// Test multiple stages // Test multiple stages
withData(data). withData(data).
terminal(s -> s.map(i -> i), terminalFunc). terminal(s -> s.map(i -> i), terminalFunc).
parallelEqualityAsserter(LambdaTestHelpers::assertContentsUnordered). resultAsserter(resultAsserter()).
exercise(); exercise();
} }
......
...@@ -133,9 +133,16 @@ public class GroupByOpTest extends OpTestCase { ...@@ -133,9 +133,16 @@ public class GroupByOpTest extends OpTestCase {
Collector<Integer, Map<Object, List<Integer>>> tab = Collectors.groupingBy(md.m); Collector<Integer, Map<Object, List<Integer>>> tab = Collectors.groupingBy(md.m);
Map<Object, List<Integer>> result = Map<Object, List<Integer>> result =
withData(data) withData(data)
.terminal(s -> s, s -> s.collect(tab)) .terminal(s -> s, s -> s.collect(tab))
.parallelEqualityAsserter(s -> StreamOpFlagTestHelper.isStreamOrdered(s) ? GroupByOpTest::assertObjectEquals : GroupByOpTest::assertMultiMapEquals) .resultAsserter((act, exp, ord, par) -> {
.exercise(); if (par & !ord) {
GroupByOpTest.assertMultiMapEquals(act, exp);
}
else {
GroupByOpTest.assertObjectEquals(act, exp);
}
})
.exercise();
assertEquals(result.keySet().size(), md.expectedSize); assertEquals(result.keySet().size(), md.expectedSize);
} }
} }
......
...@@ -145,6 +145,7 @@ public class IntSliceOpTest extends OpTestCase { ...@@ -145,6 +145,7 @@ public class IntSliceOpTest extends OpTestCase {
List<Integer> skips = sizes(data.size()); List<Integer> skips = sizes(data.size());
for (int s : skips) { for (int s : skips) {
setContext("skip", s);
Collection<Integer> sr = exerciseOps(data, st -> st.substream(s)); Collection<Integer> sr = exerciseOps(data, st -> st.substream(s));
assertEquals(sr.size(), sliceSize(data.size(), s)); assertEquals(sr.size(), sliceSize(data.size(), s));
...@@ -159,7 +160,9 @@ public class IntSliceOpTest extends OpTestCase { ...@@ -159,7 +160,9 @@ public class IntSliceOpTest extends OpTestCase {
List<Integer> limits = skips; List<Integer> limits = skips;
for (int s : skips) { for (int s : skips) {
setContext("skip", s);
for (int limit : limits) { for (int limit : limits) {
setContext("limit", limit);
Collection<Integer> sr = exerciseOps(data, st -> st.substream(s).limit(limit)); Collection<Integer> sr = exerciseOps(data, st -> st.substream(s).limit(limit));
assertEquals(sr.size(), sliceSize(sliceSize(data.size(), s), 0, limit)); assertEquals(sr.size(), sliceSize(sliceSize(data.size(), s), 0, limit));
...@@ -174,6 +177,7 @@ public class IntSliceOpTest extends OpTestCase { ...@@ -174,6 +177,7 @@ public class IntSliceOpTest extends OpTestCase {
List<Integer> limits = sizes(data.size()); List<Integer> limits = sizes(data.size());
for (int limit : limits) { for (int limit : limits) {
setContext("limit", limit);
Collection<Integer> sr = exerciseOps(data, st -> st.limit(limit)); Collection<Integer> sr = exerciseOps(data, st -> st.limit(limit));
assertEquals(sr.size(), sliceSize(data.size(), 0, limit)); assertEquals(sr.size(), sliceSize(data.size(), 0, limit));
...@@ -189,6 +193,7 @@ public class IntSliceOpTest extends OpTestCase { ...@@ -189,6 +193,7 @@ public class IntSliceOpTest extends OpTestCase {
@Test(groups = { "serialization-hostile" }) @Test(groups = { "serialization-hostile" })
public void testLimitShortCircuit() { public void testLimitShortCircuit() {
for (int l : Arrays.asList(0, 10)) { for (int l : Arrays.asList(0, 10)) {
setContext("limit", l);
AtomicInteger ai = new AtomicInteger(); AtomicInteger ai = new AtomicInteger();
IntStream.range(1, 101) IntStream.range(1, 101)
.peek(i -> ai.getAndIncrement()) .peek(i -> ai.getAndIncrement())
......
...@@ -60,7 +60,6 @@ public class IntUniqOpTest extends OpTestCase { ...@@ -60,7 +60,6 @@ public class IntUniqOpTest extends OpTestCase {
public void testOpSorted(String name, TestData.OfInt data) { public void testOpSorted(String name, TestData.OfInt data) {
Collection<Integer> result = withData(data). Collection<Integer> result = withData(data).
stream(s -> s.sorted().distinct().boxed()). stream(s -> s.sorted().distinct().boxed()).
parallelEqualityAsserter(LambdaTestHelpers::assertContentsUnordered).
exercise(); exercise();
assertUnique(result); assertUnique(result);
......
...@@ -23,19 +23,16 @@ ...@@ -23,19 +23,16 @@
package org.openjdk.tests.java.util.stream; package org.openjdk.tests.java.util.stream;
import java.util.Arrays; import java.util.Arrays;
import java.util.Collections;
import java.util.HashMap; import java.util.HashMap;
import java.util.Iterator; import java.util.Iterator;
import java.util.List; import java.util.List;
import java.util.Map; import java.util.Map;
import java.util.PrimitiveIterator; import java.util.PrimitiveIterator;
import java.util.Spliterators;
import java.util.function.DoublePredicate; import java.util.function.DoublePredicate;
import java.util.function.DoubleSupplier;
import java.util.function.Function; import java.util.function.Function;
import java.util.function.IntPredicate; import java.util.function.IntPredicate;
import java.util.function.IntSupplier;
import java.util.function.LongPredicate; import java.util.function.LongPredicate;
import java.util.function.LongSupplier;
import java.util.function.Predicate; import java.util.function.Predicate;
import java.util.function.Supplier; import java.util.function.Supplier;
import java.util.stream.DoubleStream; import java.util.stream.DoubleStream;
...@@ -46,6 +43,7 @@ import java.util.stream.LongStream; ...@@ -46,6 +43,7 @@ import java.util.stream.LongStream;
import java.util.stream.LongStreamTestDataProvider; import java.util.stream.LongStreamTestDataProvider;
import java.util.stream.OpTestCase; import java.util.stream.OpTestCase;
import java.util.stream.Stream; import java.util.stream.Stream;
import java.util.stream.StreamSupport;
import java.util.stream.StreamTestDataProvider; import java.util.stream.StreamTestDataProvider;
import java.util.stream.TestData; import java.util.stream.TestData;
...@@ -97,6 +95,7 @@ public class MatchOpTest extends OpTestCase { ...@@ -97,6 +95,7 @@ public class MatchOpTest extends OpTestCase {
private <T> void assertPredicates(List<T> source, Kind kind, Predicate<T>[] predicates, boolean... answers) { private <T> void assertPredicates(List<T> source, Kind kind, Predicate<T>[] predicates, boolean... answers) {
for (int i = 0; i < predicates.length; i++) { for (int i = 0; i < predicates.length; i++) {
setContext("i", i);
boolean match = this.<T>kinds().get(kind).apply(predicates[i]).apply(source.stream()); boolean match = this.<T>kinds().get(kind).apply(predicates[i]).apply(source.stream());
assertEquals(answers[i], match, kind.toString() + predicates[i].toString()); assertEquals(answers[i], match, kind.toString() + predicates[i].toString());
} }
...@@ -119,7 +118,9 @@ public class MatchOpTest extends OpTestCase { ...@@ -119,7 +118,9 @@ public class MatchOpTest extends OpTestCase {
@Test(dataProvider = "StreamTestData<Integer>", dataProviderClass = StreamTestDataProvider.class) @Test(dataProvider = "StreamTestData<Integer>", dataProviderClass = StreamTestDataProvider.class)
public void testStream(String name, TestData.OfRef<Integer> data) { public void testStream(String name, TestData.OfRef<Integer> data) {
for (Predicate<Integer> p : INTEGER_PREDICATES) { for (Predicate<Integer> p : INTEGER_PREDICATES) {
setContext("p", p);
for (Kind kind : Kind.values()) { for (Kind kind : Kind.values()) {
setContext("kind", kind);
exerciseTerminalOps(data, this.<Integer>kinds().get(kind).apply(p)); exerciseTerminalOps(data, this.<Integer>kinds().get(kind).apply(p));
exerciseTerminalOps(data, s -> s.filter(pFalse), this.<Integer>kinds().get(kind).apply(p)); exerciseTerminalOps(data, s -> s.filter(pFalse), this.<Integer>kinds().get(kind).apply(p));
exerciseTerminalOps(data, s -> s.filter(pEven), this.<Integer>kinds().get(kind).apply(p)); exerciseTerminalOps(data, s -> s.filter(pEven), this.<Integer>kinds().get(kind).apply(p));
...@@ -128,29 +129,40 @@ public class MatchOpTest extends OpTestCase { ...@@ -128,29 +129,40 @@ public class MatchOpTest extends OpTestCase {
} }
public void testInfinite() { public void testInfinite() {
class CycleSupplier<T> implements Supplier<T> { class CycleIterator implements Iterator<Integer> {
final Iterable<T> source; final Supplier<Iterator<Integer>> source;
Iterator<T> i = Collections.emptyIterator(); Iterator<Integer> i = null;
CycleSupplier(Iterable<T> source) { CycleIterator(Supplier<Iterator<Integer>> source) {
this.source = source; this.source = source;
} }
@Override @Override
public T get() { public Integer next() {
if (!i.hasNext()) { if (i == null || !i.hasNext()) {
i = source.iterator(); i = source.get();
} }
return i.next(); return i.next();
} }
@Override
public boolean hasNext() {
if (i == null || !i.hasNext()) {
i = source.get();
}
return i.hasNext();
}
} }
assertFalse(Stream.generate(new CycleSupplier<>(Arrays.asList(1, 2, 3, 4))).allMatch(i -> i > 3)); Supplier<Iterator<Integer>> source = () -> Arrays.asList(1, 2, 3, 4).iterator();
assertTrue(Stream.generate(new CycleSupplier<>(Arrays.asList(1, 2, 3, 4))).anyMatch(i -> i > 3)); Supplier<Stream<Integer>> s = () -> StreamSupport.stream(Spliterators.spliteratorUnknownSize(new CycleIterator(source), 0));
assertFalse(Stream.generate(new CycleSupplier<>(Arrays.asList(1, 2, 3, 4))).noneMatch(i -> i > 3));
assertFalse(Stream.generate(new CycleSupplier<>(Arrays.asList(1, 2, 3, 4))).parallel().allMatch(i -> i > 3)); assertFalse(s.get().allMatch(i -> i > 3));
assertTrue(Stream.generate(new CycleSupplier<>(Arrays.asList(1, 2, 3, 4))).parallel().anyMatch(i -> i > 3)); assertTrue(s.get().anyMatch(i -> i > 3));
assertFalse(Stream.generate(new CycleSupplier<>(Arrays.asList(1, 2, 3, 4))).parallel().noneMatch(i -> i > 3)); assertFalse(s.get().noneMatch(i -> i > 3));
assertFalse(s.get().parallel().allMatch(i -> i > 3));
assertTrue(s.get().parallel().anyMatch(i -> i > 3));
assertFalse(s.get().parallel().noneMatch(i -> i > 3));
} }
// //
...@@ -168,6 +180,7 @@ public class MatchOpTest extends OpTestCase { ...@@ -168,6 +180,7 @@ public class MatchOpTest extends OpTestCase {
private void assertIntPredicates(Supplier<IntStream> source, Kind kind, IntPredicate[] predicates, boolean... answers) { private void assertIntPredicates(Supplier<IntStream> source, Kind kind, IntPredicate[] predicates, boolean... answers) {
for (int i = 0; i < predicates.length; i++) { for (int i = 0; i < predicates.length; i++) {
setContext("i", i);
boolean match = intKinds.get(kind).apply(predicates[i]).apply(source.get()); boolean match = intKinds.get(kind).apply(predicates[i]).apply(source.get());
assertEquals(answers[i], match, kind.toString() + predicates[i].toString()); assertEquals(answers[i], match, kind.toString() + predicates[i].toString());
} }
...@@ -189,40 +202,52 @@ public class MatchOpTest extends OpTestCase { ...@@ -189,40 +202,52 @@ public class MatchOpTest extends OpTestCase {
@Test(dataProvider = "IntStreamTestData", dataProviderClass = IntStreamTestDataProvider.class) @Test(dataProvider = "IntStreamTestData", dataProviderClass = IntStreamTestDataProvider.class)
public void testIntStream(String name, TestData.OfInt data) { public void testIntStream(String name, TestData.OfInt data) {
for (IntPredicate p : INT_PREDICATES) for (IntPredicate p : INT_PREDICATES) {
setContext("p", p);
for (Kind kind : Kind.values()) { for (Kind kind : Kind.values()) {
setContext("kind", kind);
exerciseTerminalOps(data, intKinds.get(kind).apply(p)); exerciseTerminalOps(data, intKinds.get(kind).apply(p));
exerciseTerminalOps(data, s -> s.filter(ipFalse), intKinds.get(kind).apply(p)); exerciseTerminalOps(data, s -> s.filter(ipFalse), intKinds.get(kind).apply(p));
exerciseTerminalOps(data, s -> s.filter(ipEven), intKinds.get(kind).apply(p)); exerciseTerminalOps(data, s -> s.filter(ipEven), intKinds.get(kind).apply(p));
} }
}
} }
public void testIntInfinite() { public void testIntInfinite() {
class CycleSupplier implements IntSupplier { class CycleIterator implements PrimitiveIterator.OfInt {
final Supplier<PrimitiveIterator.OfInt> source; final Supplier<PrimitiveIterator.OfInt> source;
PrimitiveIterator.OfInt i = null; PrimitiveIterator.OfInt i = null;
CycleSupplier(Supplier<PrimitiveIterator.OfInt> source) { CycleIterator(Supplier<PrimitiveIterator.OfInt> source) {
this.source = source; this.source = source;
} }
@Override @Override
public int getAsInt() { public int nextInt() {
if (i == null || !i.hasNext()) { if (i == null || !i.hasNext()) {
i = source.get(); i = source.get();
} }
return i.nextInt(); return i.nextInt();
} }
@Override
public boolean hasNext() {
if (i == null || !i.hasNext()) {
i = source.get();
}
return i.hasNext();
}
} }
Supplier<PrimitiveIterator.OfInt> source = () -> Arrays.stream(new int[]{1, 2, 3, 4}).iterator(); Supplier<PrimitiveIterator.OfInt> source = () -> Arrays.stream(new int[]{1, 2, 3, 4}).iterator();
Supplier<IntStream> s = () -> StreamSupport.intStream(Spliterators.spliteratorUnknownSize(new CycleIterator(source), 0));
assertFalse(IntStream.generate(new CycleSupplier(source)).allMatch(i -> i > 3));
assertTrue(IntStream.generate(new CycleSupplier(source)).anyMatch(i -> i > 3)); assertFalse(s.get().allMatch(i -> i > 3));
assertFalse(IntStream.generate(new CycleSupplier(source)).noneMatch(i -> i > 3)); assertTrue(s.get().anyMatch(i -> i > 3));
assertFalse(IntStream.generate(new CycleSupplier(source)).parallel().allMatch(i -> i > 3)); assertFalse(s.get().noneMatch(i -> i > 3));
assertTrue(IntStream.generate(new CycleSupplier(source)).parallel().anyMatch(i -> i > 3)); assertFalse(s.get().parallel().allMatch(i -> i > 3));
assertFalse(IntStream.generate(new CycleSupplier(source)).parallel().noneMatch(i -> i > 3)); assertTrue(s.get().parallel().anyMatch(i -> i > 3));
assertFalse(s.get().parallel().noneMatch(i -> i > 3));
} }
// //
...@@ -240,6 +265,7 @@ public class MatchOpTest extends OpTestCase { ...@@ -240,6 +265,7 @@ public class MatchOpTest extends OpTestCase {
private void assertLongPredicates(Supplier<LongStream> source, Kind kind, LongPredicate[] predicates, boolean... answers) { private void assertLongPredicates(Supplier<LongStream> source, Kind kind, LongPredicate[] predicates, boolean... answers) {
for (int i = 0; i < predicates.length; i++) { for (int i = 0; i < predicates.length; i++) {
setContext("i", i);
boolean match = longKinds.get(kind).apply(predicates[i]).apply(source.get()); boolean match = longKinds.get(kind).apply(predicates[i]).apply(source.get());
assertEquals(answers[i], match, kind.toString() + predicates[i].toString()); assertEquals(answers[i], match, kind.toString() + predicates[i].toString());
} }
...@@ -261,40 +287,52 @@ public class MatchOpTest extends OpTestCase { ...@@ -261,40 +287,52 @@ public class MatchOpTest extends OpTestCase {
@Test(dataProvider = "LongStreamTestData", dataProviderClass = LongStreamTestDataProvider.class) @Test(dataProvider = "LongStreamTestData", dataProviderClass = LongStreamTestDataProvider.class)
public void testLongStream(String name, TestData.OfLong data) { public void testLongStream(String name, TestData.OfLong data) {
for (LongPredicate p : LONG_PREDICATES) for (LongPredicate p : LONG_PREDICATES) {
setContext("p", p);
for (Kind kind : Kind.values()) { for (Kind kind : Kind.values()) {
setContext("kind", kind);
exerciseTerminalOps(data, longKinds.get(kind).apply(p)); exerciseTerminalOps(data, longKinds.get(kind).apply(p));
exerciseTerminalOps(data, s -> s.filter(lpFalse), longKinds.get(kind).apply(p)); exerciseTerminalOps(data, s -> s.filter(lpFalse), longKinds.get(kind).apply(p));
exerciseTerminalOps(data, s -> s.filter(lpEven), longKinds.get(kind).apply(p)); exerciseTerminalOps(data, s -> s.filter(lpEven), longKinds.get(kind).apply(p));
} }
}
} }
public void testLongInfinite() { public void testLongInfinite() {
class CycleSupplier implements LongSupplier { class CycleIterator implements PrimitiveIterator.OfLong {
final Supplier<PrimitiveIterator.OfLong> source; final Supplier<PrimitiveIterator.OfLong> source;
PrimitiveIterator.OfLong i = null; PrimitiveIterator.OfLong i = null;
CycleSupplier(Supplier<PrimitiveIterator.OfLong> source) { CycleIterator(Supplier<PrimitiveIterator.OfLong> source) {
this.source = source; this.source = source;
} }
@Override @Override
public long getAsLong() { public long nextLong() {
if (i == null || !i.hasNext()) { if (i == null || !i.hasNext()) {
i = source.get(); i = source.get();
} }
return i.nextLong(); return i.nextLong();
} }
@Override
public boolean hasNext() {
if (i == null || !i.hasNext()) {
i = source.get();
}
return i.hasNext();
}
} }
Supplier<PrimitiveIterator.OfLong> source = () -> Arrays.stream(new long[]{1, 2, 3, 4}).iterator(); Supplier<PrimitiveIterator.OfLong> source = () -> Arrays.stream(new long[]{1, 2, 3, 4}).iterator();
Supplier<LongStream> s = () -> StreamSupport.longStream(Spliterators.spliteratorUnknownSize(new CycleIterator(source), 0));
assertFalse(LongStream.generate(new CycleSupplier(source)).allMatch(i -> i > 3));
assertTrue(LongStream.generate(new CycleSupplier(source)).anyMatch(i -> i > 3)); assertFalse(s.get().allMatch(i -> i > 3));
assertFalse(LongStream.generate(new CycleSupplier(source)).noneMatch(i -> i > 3)); assertTrue(s.get().anyMatch(i -> i > 3));
assertFalse(LongStream.generate(new CycleSupplier(source)).parallel().allMatch(i -> i > 3)); assertFalse(s.get().noneMatch(i -> i > 3));
assertTrue(LongStream.generate(new CycleSupplier(source)).parallel().anyMatch(i -> i > 3)); assertFalse(s.get().parallel().allMatch(i -> i > 3));
assertFalse(LongStream.generate(new CycleSupplier(source)).parallel().noneMatch(i -> i > 3)); assertTrue(s.get().parallel().anyMatch(i -> i > 3));
assertFalse(s.get().parallel().noneMatch(i -> i > 3));
} }
// //
...@@ -312,6 +350,7 @@ public class MatchOpTest extends OpTestCase { ...@@ -312,6 +350,7 @@ public class MatchOpTest extends OpTestCase {
private void assertDoublePredicates(Supplier<DoubleStream> source, Kind kind, DoublePredicate[] predicates, boolean... answers) { private void assertDoublePredicates(Supplier<DoubleStream> source, Kind kind, DoublePredicate[] predicates, boolean... answers) {
for (int i = 0; i < predicates.length; i++) { for (int i = 0; i < predicates.length; i++) {
setContext("i", i);
boolean match = doubleKinds.get(kind).apply(predicates[i]).apply(source.get()); boolean match = doubleKinds.get(kind).apply(predicates[i]).apply(source.get());
assertEquals(answers[i], match, kind.toString() + predicates[i].toString()); assertEquals(answers[i], match, kind.toString() + predicates[i].toString());
} }
...@@ -333,39 +372,51 @@ public class MatchOpTest extends OpTestCase { ...@@ -333,39 +372,51 @@ public class MatchOpTest extends OpTestCase {
@Test(dataProvider = "DoubleStreamTestData", dataProviderClass = DoubleStreamTestDataProvider.class) @Test(dataProvider = "DoubleStreamTestData", dataProviderClass = DoubleStreamTestDataProvider.class)
public void testDoubleStream(String name, TestData.OfDouble data) { public void testDoubleStream(String name, TestData.OfDouble data) {
for (DoublePredicate p : DOUBLE_PREDICATES) for (DoublePredicate p : DOUBLE_PREDICATES) {
setContext("p", p);
for (Kind kind : Kind.values()) { for (Kind kind : Kind.values()) {
setContext("kind", kind);
exerciseTerminalOps(data, doubleKinds.get(kind).apply(p)); exerciseTerminalOps(data, doubleKinds.get(kind).apply(p));
exerciseTerminalOps(data, s -> s.filter(dpFalse), doubleKinds.get(kind).apply(p)); exerciseTerminalOps(data, s -> s.filter(dpFalse), doubleKinds.get(kind).apply(p));
exerciseTerminalOps(data, s -> s.filter(dpEven), doubleKinds.get(kind).apply(p)); exerciseTerminalOps(data, s -> s.filter(dpEven), doubleKinds.get(kind).apply(p));
} }
}
} }
public void testDoubleInfinite() { public void testDoubleInfinite() {
class CycleSupplier implements DoubleSupplier { class CycleIterator implements PrimitiveIterator.OfDouble {
final Supplier<PrimitiveIterator.OfDouble> source; final Supplier<PrimitiveIterator.OfDouble> source;
PrimitiveIterator.OfDouble i = null; PrimitiveIterator.OfDouble i = null;
CycleSupplier(Supplier<PrimitiveIterator.OfDouble> source) { CycleIterator(Supplier<PrimitiveIterator.OfDouble> source) {
this.source = source; this.source = source;
} }
@Override @Override
public double getAsDouble() { public double nextDouble() {
if (i == null || !i.hasNext()) { if (i == null || !i.hasNext()) {
i = source.get(); i = source.get();
} }
return i.nextDouble(); return i.nextDouble();
} }
@Override
public boolean hasNext() {
if (i == null || !i.hasNext()) {
i = source.get();
}
return i.hasNext();
}
} }
Supplier<PrimitiveIterator.OfDouble> source = () -> Arrays.stream(new double[]{1, 2, 3, 4}).iterator(); Supplier<PrimitiveIterator.OfDouble> source = () -> Arrays.stream(new double[]{1, 2, 3, 4}).iterator();
Supplier<DoubleStream> s = () -> StreamSupport.doubleStream(Spliterators.spliteratorUnknownSize(new CycleIterator(source), 0));
assertFalse(DoubleStream.generate(new CycleSupplier(source)).allMatch(i -> i > 3));
assertTrue(DoubleStream.generate(new CycleSupplier(source)).anyMatch(i -> i > 3)); assertFalse(s.get().allMatch(i -> i > 3));
assertFalse(DoubleStream.generate(new CycleSupplier(source)).noneMatch(i -> i > 3)); assertTrue(s.get().anyMatch(i -> i > 3));
assertFalse(DoubleStream.generate(new CycleSupplier(source)).parallel().allMatch(i -> i > 3)); assertFalse(s.get().noneMatch(i -> i > 3));
assertTrue(DoubleStream.generate(new CycleSupplier(source)).parallel().anyMatch(i -> i > 3)); assertFalse(s.get().parallel().allMatch(i -> i > 3));
assertFalse(DoubleStream.generate(new CycleSupplier(source)).parallel().noneMatch(i -> i > 3)); assertTrue(s.get().parallel().anyMatch(i -> i > 3));
assertFalse(s.get().parallel().noneMatch(i -> i > 3));
} }
} }
...@@ -58,7 +58,9 @@ public class RangeTest extends OpTestCase { ...@@ -58,7 +58,9 @@ public class RangeTest extends OpTestCase {
public void testIntRange() { public void testIntRange() {
// Half-open // Half-open
for (int start : Arrays.asList(1, 10, -1, -10)) { for (int start : Arrays.asList(1, 10, -1, -10)) {
setContext("start", start);
for (int end : Arrays.asList(1, 10, -1, -10)) { for (int end : Arrays.asList(1, 10, -1, -10)) {
setContext("end", end);
int size = (start < end) ? end - start : 0; int size = (start < end) ? end - start : 0;
int[] exp = new int[size]; int[] exp = new int[size];
for (int i = start, p = 0; i < end; i++, p++) { for (int i = start, p = 0; i < end; i++, p++) {
...@@ -76,7 +78,9 @@ public class RangeTest extends OpTestCase { ...@@ -76,7 +78,9 @@ public class RangeTest extends OpTestCase {
// Closed // Closed
for (int start : Arrays.asList(1, 10, -1, -10)) { for (int start : Arrays.asList(1, 10, -1, -10)) {
setContext("start", start);
for (int end : Arrays.asList(1, 10, -1, -10)) { for (int end : Arrays.asList(1, 10, -1, -10)) {
setContext("end", end);
int size = (start <= end) ? end - start + 1 : 0; int size = (start <= end) ? end - start + 1 : 0;
int[] exp = new int[size]; int[] exp = new int[size];
for (int i = start, p = 0; i <= end; i++, p++) { for (int i = start, p = 0; i <= end; i++, p++) {
...@@ -144,7 +148,9 @@ public class RangeTest extends OpTestCase { ...@@ -144,7 +148,9 @@ public class RangeTest extends OpTestCase {
public void testLongRange() { public void testLongRange() {
// Half-open // Half-open
for (long start : Arrays.asList(1, 1000, -1, -1000)) { for (long start : Arrays.asList(1, 1000, -1, -1000)) {
setContext("start", start);
for (long end : Arrays.asList(1, 1000, -1, -1000)) { for (long end : Arrays.asList(1, 1000, -1, -1000)) {
setContext("end", end);
long size = start < end ? end - start : 0; long size = start < end ? end - start : 0;
long[] exp = new long[(int) size]; long[] exp = new long[(int) size];
for (long i = start, p = 0; i < end; i++, p++) { for (long i = start, p = 0; i < end; i++, p++) {
...@@ -162,7 +168,9 @@ public class RangeTest extends OpTestCase { ...@@ -162,7 +168,9 @@ public class RangeTest extends OpTestCase {
// Closed // Closed
for (long start : Arrays.asList(1, 1000, -1, -1000)) { for (long start : Arrays.asList(1, 1000, -1, -1000)) {
setContext("start", start);
for (long end : Arrays.asList(1, 1000, -1, -1000)) { for (long end : Arrays.asList(1, 1000, -1, -1000)) {
setContext("end", end);
long size = start <= end ? end - start + 1: 0; long size = start <= end ? end - start + 1: 0;
long[] exp = new long[(int) size]; long[] exp = new long[(int) size];
for (long i = start, p = 0; i <= end; i++, p++) { for (long i = start, p = 0; i <= end; i++, p++) {
......
...@@ -51,6 +51,7 @@ public class ReduceByOpTest extends OpTestCase { ...@@ -51,6 +51,7 @@ public class ReduceByOpTest extends OpTestCase {
Map<Boolean, Integer> result = data.stream().collect(groupingBy(LambdaTestHelpers.forPredicate(pEven, true, false), reducing(0, rPlus))); Map<Boolean, Integer> result = data.stream().collect(groupingBy(LambdaTestHelpers.forPredicate(pEven, true, false), reducing(0, rPlus)));
assertEquals(result.size(), gbResult.size()); assertEquals(result.size(), gbResult.size());
for (Map.Entry<Boolean, Integer> entry : result.entrySet()) { for (Map.Entry<Boolean, Integer> entry : result.entrySet()) {
setContext("entry", entry);
Boolean key = entry.getKey(); Boolean key = entry.getKey();
assertEquals(entry.getValue(), data.stream().filter(e -> pEven.test(e) == key).reduce(0, rPlus)); assertEquals(entry.getValue(), data.stream().filter(e -> pEven.test(e) == key).reduce(0, rPlus));
} }
...@@ -59,7 +60,9 @@ public class ReduceByOpTest extends OpTestCase { ...@@ -59,7 +60,9 @@ public class ReduceByOpTest extends OpTestCase {
Map<Integer, List<Integer>> mgResult = exerciseTerminalOps(data, s -> s.collect(groupingBy(mId))); Map<Integer, List<Integer>> mgResult = exerciseTerminalOps(data, s -> s.collect(groupingBy(mId)));
Map<Integer, Integer> miResult = exerciseTerminalOps(data, s -> s.collect(groupingBy(mId, reducing(0, e -> 1, Integer::sum)))); Map<Integer, Integer> miResult = exerciseTerminalOps(data, s -> s.collect(groupingBy(mId, reducing(0, e -> 1, Integer::sum))));
assertEquals(miResult.keySet().size(), uniqueSize); assertEquals(miResult.keySet().size(), uniqueSize);
for (Map.Entry<Integer, Integer> entry : miResult.entrySet()) for (Map.Entry<Integer, Integer> entry : miResult.entrySet()) {
setContext("entry", entry);
assertEquals((int) entry.getValue(), mgResult.get(entry.getKey()).size()); assertEquals((int) entry.getValue(), mgResult.get(entry.getKey()).size());
}
} }
} }
...@@ -22,13 +22,14 @@ ...@@ -22,13 +22,14 @@
*/ */
package org.openjdk.tests.java.util.stream; package org.openjdk.tests.java.util.stream;
import java.util.Comparators;
import java.util.stream.LambdaTestHelpers; import java.util.stream.LambdaTestHelpers;
import java.util.stream.OpTestCase; import java.util.stream.OpTestCase;
import java.util.stream.StreamTestDataProvider; import java.util.stream.StreamTestDataProvider;
import org.testng.annotations.Test; import org.testng.annotations.Test;
import java.util.Comparators;
import java.util.Iterator; import java.util.Iterator;
import java.util.Comparator;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.function.Function; import java.util.function.Function;
import java.util.function.Supplier; import java.util.function.Supplier;
...@@ -64,8 +65,12 @@ public class SequentialOpTest extends OpTestCase { ...@@ -64,8 +65,12 @@ public class SequentialOpTest extends OpTestCase {
(UnaryOperator<Stream<Integer>>) s -> s.parallel().map(id).peek(e -> { counter.incrementAndGet(); }).map(id) (UnaryOperator<Stream<Integer>>) s -> s.parallel().map(id).peek(e -> { counter.incrementAndGet(); }).map(id)
}; };
for (Supplier<Stream<Integer>> supp : suppliers) for (int i = 0; i < suppliers.length; i++) {
for (UnaryOperator<Stream<Integer>> config : configs) { setContext("supplierIndex", i);
Supplier<Stream<Integer>> supp = suppliers[i];
for (int j = 0; j < configs.length; j++) {
setContext("configIndex", j);
UnaryOperator<Stream<Integer>> config = configs[j];
counter.set(0); counter.set(0);
Stream<Integer> stream = config.apply(supp.get()); Stream<Integer> stream = config.apply(supp.get());
assertEquals(0, counter.get()); assertEquals(0, counter.get());
...@@ -86,6 +91,7 @@ public class SequentialOpTest extends OpTestCase { ...@@ -86,6 +91,7 @@ public class SequentialOpTest extends OpTestCase {
}); });
assertTrue(data.size() == 0 || counter.get() > 0); assertTrue(data.size() == 0 || counter.get() > 0);
} }
}
} }
@SuppressWarnings({"rawtypes", "unchecked"}) @SuppressWarnings({"rawtypes", "unchecked"})
...@@ -96,7 +102,8 @@ public class SequentialOpTest extends OpTestCase { ...@@ -96,7 +102,8 @@ public class SequentialOpTest extends OpTestCase {
= new UnaryOperator[] { = new UnaryOperator[] {
(UnaryOperator<Stream<Integer>>) s -> s, (UnaryOperator<Stream<Integer>>) s -> s,
(UnaryOperator<Stream<Integer>>) s -> s.sequential(), (UnaryOperator<Stream<Integer>>) s -> s.sequential(),
(UnaryOperator<Stream<Integer>>) s -> s.parallel() (UnaryOperator<Stream<Integer>>) s -> s.parallel(),
(UnaryOperator<Stream<Integer>>) s -> s.unordered()
}; };
UnaryOperator<Stream<Integer>>[] stuff UnaryOperator<Stream<Integer>>[] stuff
= new UnaryOperator[] { = new UnaryOperator[] {
...@@ -107,12 +114,23 @@ public class SequentialOpTest extends OpTestCase { ...@@ -107,12 +114,23 @@ public class SequentialOpTest extends OpTestCase {
(UnaryOperator<Stream<Integer>>) s -> s.filter(LambdaTestHelpers.pEven).sorted(Comparators.naturalOrder()).map(id), (UnaryOperator<Stream<Integer>>) s -> s.filter(LambdaTestHelpers.pEven).sorted(Comparators.naturalOrder()).map(id),
}; };
for (UnaryOperator<Stream<Integer>> c1 : changers) for (int c1Index = 0; c1Index < changers.length; c1Index++) {
for (UnaryOperator<Stream<Integer>> s1 : stuff) setContext("c1Index", c1Index);
for (UnaryOperator<Stream<Integer>> c2 : changers) UnaryOperator<Stream<Integer>> c1 = changers[c1Index];
for (UnaryOperator<Stream<Integer>> s2 : stuff) { for (int s1Index = 0; s1Index < stuff.length; s1Index++) {
setContext("s1Index", s1Index);
UnaryOperator<Stream<Integer>> s1 = stuff[s1Index];
for (int c2Index = 0; c2Index < changers.length; c2Index++) {
setContext("c2Index", c2Index);
UnaryOperator<Stream<Integer>> c2 = changers[c2Index];
for (int s2Index = 0; s2Index < stuff.length; s2Index++) {
setContext("s2Index", s2Index);
UnaryOperator<Stream<Integer>> s2 = stuff[s2Index];
UnaryOperator<Stream<Integer>> composed = s -> s2.apply(c2.apply(s1.apply(c1.apply(s)))); UnaryOperator<Stream<Integer>> composed = s -> s2.apply(c2.apply(s1.apply(c1.apply(s))));
exerciseOps(data, composed); exerciseOps(data, composed);
} }
}
}
}
} }
} }
...@@ -26,7 +26,11 @@ import org.testng.annotations.Test; ...@@ -26,7 +26,11 @@ import org.testng.annotations.Test;
import java.util.*; import java.util.*;
import java.util.concurrent.atomic.AtomicInteger; import java.util.concurrent.atomic.AtomicInteger;
import java.util.stream.Collectors; import java.util.function.Function;
import java.util.stream.DoubleStream;
import java.util.stream.IntStream;
import java.util.stream.LambdaTestHelpers;
import java.util.stream.LongStream;
import java.util.stream.OpTestCase; import java.util.stream.OpTestCase;
import java.util.stream.Stream; import java.util.stream.Stream;
import java.util.stream.StreamTestDataProvider; import java.util.stream.StreamTestDataProvider;
...@@ -145,19 +149,20 @@ public class SliceOpTest extends OpTestCase { ...@@ -145,19 +149,20 @@ public class SliceOpTest extends OpTestCase {
List<Integer> skips = sizes(data.size()); List<Integer> skips = sizes(data.size());
for (int s : skips) { for (int s : skips) {
Collection<Integer> sr = exerciseOpsInt(data, setContext("skip", s);
st -> st.substream(s), testSliceMulti(data,
st -> st.substream(s), sliceSize(data.size(), s),
st -> st.substream(s), st -> st.substream(s),
st -> st.substream(s)); st -> st.substream(s),
assertEquals(sr.size(), sliceSize(data.size(), s)); st -> st.substream(s),
st -> st.substream(s));
sr = exerciseOpsInt(data,
st -> st.substream(s).substream(s / 2), testSliceMulti(data,
st -> st.substream(s).substream(s / 2), sliceSize(sliceSize(data.size(), s), s/2),
st -> st.substream(s).substream(s / 2), st -> st.substream(s).substream(s / 2),
st -> st.substream(s).substream(s / 2)); st -> st.substream(s).substream(s / 2),
assertEquals(sr.size(), sliceSize(sliceSize(data.size(), s), s/2)); st -> st.substream(s).substream(s / 2),
st -> st.substream(s).substream(s / 2));
} }
} }
...@@ -167,20 +172,22 @@ public class SliceOpTest extends OpTestCase { ...@@ -167,20 +172,22 @@ public class SliceOpTest extends OpTestCase {
List<Integer> limits = skips; List<Integer> limits = skips;
for (int s : skips) { for (int s : skips) {
for (int limit : limits) { setContext("skip", s);
Collection<Integer> sr = exerciseOpsInt(data, for (int l : limits) {
st -> st.substream(s).limit(limit), setContext("limit", l);
st -> st.substream(s).limit(limit), testSliceMulti(data,
st -> st.substream(s).limit(limit), sliceSize(sliceSize(data.size(), s), 0, l),
st -> st.substream(s).limit(limit)); st -> st.substream(s).limit(l),
assertEquals(sr.size(), sliceSize(sliceSize(data.size(), s), 0, limit)); st -> st.substream(s).limit(l),
st -> st.substream(s).limit(l),
sr = exerciseOpsInt(data, st -> st.substream(s).limit(l));
st -> st.substream(s, limit+s),
st -> st.substream(s, limit+s), testSliceMulti(data,
st -> st.substream(s, limit+s), sliceSize(data.size(), s, l),
st -> st.substream(s, limit+s)); st -> st.substream(s, l+s),
assertEquals(sr.size(), sliceSize(data.size(), s, limit)); st -> st.substream(s, l+s),
st -> st.substream(s, l+s),
st -> st.substream(s, l+s));
} }
} }
} }
...@@ -189,20 +196,74 @@ public class SliceOpTest extends OpTestCase { ...@@ -189,20 +196,74 @@ public class SliceOpTest extends OpTestCase {
public void testLimitOps(String name, TestData.OfRef<Integer> data) { public void testLimitOps(String name, TestData.OfRef<Integer> data) {
List<Integer> limits = sizes(data.size()); List<Integer> limits = sizes(data.size());
for (int limit : limits) { for (int l : limits) {
Collection<Integer> sr = exerciseOpsInt(data, setContext("limit", l);
st -> st.limit(limit), testSliceMulti(data,
st -> st.limit(limit), sliceSize(data.size(), 0, l),
st -> st.limit(limit), st -> st.limit(l),
st -> st.limit(limit)); st -> st.limit(l),
assertEquals(sr.size(), sliceSize(data.size(), 0, limit)); st -> st.limit(l),
st -> st.limit(l));
sr = exerciseOpsInt(data, }
st -> st.limit(limit).limit(limit / 2),
st -> st.limit(limit).limit(limit / 2), for (int l : limits) {
st -> st.limit(limit).limit(limit / 2), setContext("limit", l);
st -> st.limit(limit).limit(limit / 2)); testSliceMulti(data,
assertEquals(sr.size(), sliceSize(sliceSize(data.size(), 0, limit), 0, limit/2)); sliceSize(sliceSize(data.size(), 0, l), 0, l / 2),
st -> st.limit(l).limit(l / 2),
st -> st.limit(l).limit(l / 2),
st -> st.limit(l).limit(l / 2),
st -> st.limit(l).limit(l / 2));
}
}
private ResultAsserter<Iterable<Integer>> sliceResultAsserter(Iterable<Integer> data,
int expectedSize) {
return (act, exp, ord, par) -> {
if (par & !ord) {
List<Integer> expected = new ArrayList<>();
data.forEach(expected::add);
List<Integer> actual = new ArrayList<>();
act.forEach(actual::add);
assertEquals(actual.size(), expectedSize);
assertTrue(expected.containsAll(actual));
}
else {
LambdaTestHelpers.assertContents(act, exp);
}
};
}
private void testSliceMulti(TestData.OfRef<Integer> data,
int expectedSize,
Function<Stream<Integer>, Stream<Integer>> mRef,
Function<IntStream, IntStream> mInt,
Function<LongStream, LongStream> mLong,
Function<DoubleStream, DoubleStream> mDouble) {
@SuppressWarnings({ "rawtypes", "unchecked" })
Function<Stream<Integer>, Stream<Integer>>[] ms = new Function[4];
ms[0] = mRef;
ms[1] = s -> mInt.apply(s.mapToInt(e -> e)).mapToObj(e -> e);
ms[2] = s -> mLong.apply(s.mapToLong(e -> e)).mapToObj(e -> (int) e);
ms[3] = s -> mDouble.apply(s.mapToDouble(e -> e)).mapToObj(e -> (int) e);
testSliceMulti(data, expectedSize, ms);
}
@SafeVarargs
private final void testSliceMulti(TestData.OfRef<Integer> data,
int expectedSize,
Function<Stream<Integer>, Stream<Integer>>... ms) {
for (int i = 0; i < ms.length; i++) {
setContext("mIndex", i);
Function<Stream<Integer>, Stream<Integer>> m = ms[i];
Collection<Integer> sr = withData(data)
.stream(m)
.resultAsserter(sliceResultAsserter(data, expectedSize))
.exercise();
assertEquals(sr.size(), expectedSize);
} }
} }
...@@ -215,6 +276,7 @@ public class SliceOpTest extends OpTestCase { ...@@ -215,6 +276,7 @@ public class SliceOpTest extends OpTestCase {
@Test(groups = { "serialization-hostile" }) @Test(groups = { "serialization-hostile" })
public void testLimitShortCircuit() { public void testLimitShortCircuit() {
for (int l : Arrays.asList(0, 10)) { for (int l : Arrays.asList(0, 10)) {
setContext("l", l);
AtomicInteger ai = new AtomicInteger(); AtomicInteger ai = new AtomicInteger();
countTo(100).stream() countTo(100).stream()
.peek(i -> ai.getAndIncrement()) .peek(i -> ai.getAndIncrement())
...@@ -224,18 +286,6 @@ public class SliceOpTest extends OpTestCase { ...@@ -224,18 +286,6 @@ public class SliceOpTest extends OpTestCase {
} }
} }
public void testSkipParallel() {
List<Integer> l = countTo(1000).parallelStream().substream(200).limit(200).sequential().collect(Collectors.toList());
assertEquals(l.size(), 200);
assertEquals(l.get(l.size() -1).intValue(), 400);
}
public void testLimitParallel() {
List<Integer> l = countTo(1000).parallelStream().limit(500).sequential().collect(Collectors.toList());
assertEquals(l.size(), 500);
assertEquals(l.get(l.size() -1).intValue(), 500);
}
private List<Integer> sizes(int size) { private List<Integer> sizes(int size) {
if (size < 4) { if (size < 4) {
return Arrays.asList(0, 1, 2, 3, 4, 6); return Arrays.asList(0, 1, 2, 3, 4, 6);
......
...@@ -47,6 +47,7 @@ public class StreamLinkTest extends OpTestCase { ...@@ -47,6 +47,7 @@ public class StreamLinkTest extends OpTestCase {
@Test(dataProvider = "StreamTestData<Integer>", dataProviderClass = StreamTestDataProvider.class) @Test(dataProvider = "StreamTestData<Integer>", dataProviderClass = StreamTestDataProvider.class)
public void testManyStreams(String name, TestData.OfRef<Integer> data) { public void testManyStreams(String name, TestData.OfRef<Integer> data) {
for (int n : sizes) { for (int n : sizes) {
setContext("n", n);
List<Integer> expected = data.stream().map(e -> (Integer) (e + n)).collect(Collectors.toList()); List<Integer> expected = data.stream().map(e -> (Integer) (e + n)).collect(Collectors.toList());
withData(data). withData(data).
...@@ -59,6 +60,7 @@ public class StreamLinkTest extends OpTestCase { ...@@ -59,6 +60,7 @@ public class StreamLinkTest extends OpTestCase {
@Test(dataProvider = "IntStreamTestData", dataProviderClass = IntStreamTestDataProvider.class) @Test(dataProvider = "IntStreamTestData", dataProviderClass = IntStreamTestDataProvider.class)
public void testIntManyStreams(String name, TestData.OfInt data) { public void testIntManyStreams(String name, TestData.OfInt data) {
for (int n : sizes) { for (int n : sizes) {
setContext("n", n);
int[] expected = data.stream().map(e -> e + n).toArray(); int[] expected = data.stream().map(e -> e + n).toArray();
withData(data). withData(data).
...@@ -71,6 +73,7 @@ public class StreamLinkTest extends OpTestCase { ...@@ -71,6 +73,7 @@ public class StreamLinkTest extends OpTestCase {
@Test(dataProvider = "LongStreamTestData", dataProviderClass = LongStreamTestDataProvider.class) @Test(dataProvider = "LongStreamTestData", dataProviderClass = LongStreamTestDataProvider.class)
public void testLongManyStreams(String name, TestData.OfLong data) { public void testLongManyStreams(String name, TestData.OfLong data) {
for (int n : sizes) { for (int n : sizes) {
setContext("n", n);
long[] expected = data.stream().map(e -> e + n).toArray(); long[] expected = data.stream().map(e -> e + n).toArray();
withData(data). withData(data).
...@@ -83,6 +86,7 @@ public class StreamLinkTest extends OpTestCase { ...@@ -83,6 +86,7 @@ public class StreamLinkTest extends OpTestCase {
@Test(dataProvider = "DoubleStreamTestData", dataProviderClass = DoubleStreamTestDataProvider.class) @Test(dataProvider = "DoubleStreamTestData", dataProviderClass = DoubleStreamTestDataProvider.class)
public void testDoubleManyStreams(String name, TestData.OfDouble data) { public void testDoubleManyStreams(String name, TestData.OfDouble data) {
for (int n : sizes) { for (int n : sizes) {
setContext("n", n);
double[] expected = data.stream().map(e -> accumulate(e, n)).toArray(); double[] expected = data.stream().map(e -> accumulate(e, n)).toArray();
withData(data). withData(data).
......
...@@ -256,9 +256,14 @@ public class StreamSpliteratorTest extends OpTestCase { ...@@ -256,9 +256,14 @@ public class StreamSpliteratorTest extends OpTestCase {
s -> s.map(LambdaTestHelpers.identity()).parallel() s -> s.map(LambdaTestHelpers.identity()).parallel()
); );
for (Consumer<Stream<Integer>> terminalOp : terminalOps) { for (int i = 0; i < terminalOps.size(); i++) {
for (UnaryOperator<Stream<Integer>> intermediateOp : intermediateOps) { setContext("termOpIndex", i);
for (boolean proxyEstimateSize : new boolean[]{false, true}) { Consumer<Stream<Integer>> terminalOp = terminalOps.get(i);
for (int j = 0; j < intermediateOps.size(); j++) {
setContext("intOpIndex", j);
UnaryOperator<Stream<Integer>> intermediateOp = intermediateOps.get(j);
for (boolean proxyEstimateSize : new boolean[] {false, true}) {
setContext("proxyEstimateSize", proxyEstimateSize);
Spliterator<Integer> sp = intermediateOp.apply(l.stream()).spliterator(); Spliterator<Integer> sp = intermediateOp.apply(l.stream()).spliterator();
ProxyNoExactSizeSpliterator<Integer> psp = new ProxyNoExactSizeSpliterator<>(sp, proxyEstimateSize); ProxyNoExactSizeSpliterator<Integer> psp = new ProxyNoExactSizeSpliterator<>(sp, proxyEstimateSize);
Stream<Integer> s = StreamSupport.parallelStream(psp); Stream<Integer> s = StreamSupport.parallelStream(psp);
...@@ -345,9 +350,14 @@ public class StreamSpliteratorTest extends OpTestCase { ...@@ -345,9 +350,14 @@ public class StreamSpliteratorTest extends OpTestCase {
s -> s.map(i -> i).parallel() s -> s.map(i -> i).parallel()
); );
for (Consumer<IntStream> terminalOp : terminalOps) { for (int i = 0; i < terminalOps.size(); i++) {
for (UnaryOperator<IntStream> intermediateOp : intermediateOps) { setContext("termOpIndex", i);
for (boolean proxyEstimateSize : new boolean[]{false, true}) { Consumer<IntStream> terminalOp = terminalOps.get(i);
for (int j = 0; j < intermediateOps.size(); j++) {
setContext("intOpIndex", j);
UnaryOperator<IntStream> intermediateOp = intermediateOps.get(j);
for (boolean proxyEstimateSize : new boolean[] {false, true}) {
setContext("proxyEstimateSize", proxyEstimateSize);
// Size is assumed to be larger than the target size for no splitting // Size is assumed to be larger than the target size for no splitting
// @@@ Need way to obtain the target size // @@@ Need way to obtain the target size
Spliterator.OfInt sp = intermediateOp.apply(IntStream.range(0, 1000)).spliterator(); Spliterator.OfInt sp = intermediateOp.apply(IntStream.range(0, 1000)).spliterator();
...@@ -433,9 +443,14 @@ public class StreamSpliteratorTest extends OpTestCase { ...@@ -433,9 +443,14 @@ public class StreamSpliteratorTest extends OpTestCase {
s -> s.map(i -> i).parallel() s -> s.map(i -> i).parallel()
); );
for (Consumer<LongStream> terminalOp : terminalOps) { for (int i = 0; i < terminalOps.size(); i++) {
for (UnaryOperator<LongStream> intermediateOp : intermediateOps) { Consumer<LongStream> terminalOp = terminalOps.get(i);
for (boolean proxyEstimateSize : new boolean[]{false, true}) { setContext("termOpIndex", i);
for (int j = 0; j < intermediateOps.size(); j++) {
setContext("intOpIndex", j);
UnaryOperator<LongStream> intermediateOp = intermediateOps.get(j);
for (boolean proxyEstimateSize : new boolean[] {false, true}) {
setContext("proxyEstimateSize", proxyEstimateSize);
// Size is assumed to be larger than the target size for no splitting // Size is assumed to be larger than the target size for no splitting
// @@@ Need way to obtain the target size // @@@ Need way to obtain the target size
Spliterator.OfLong sp = intermediateOp.apply(LongStream.range(0, 1000)).spliterator(); Spliterator.OfLong sp = intermediateOp.apply(LongStream.range(0, 1000)).spliterator();
...@@ -521,9 +536,14 @@ public class StreamSpliteratorTest extends OpTestCase { ...@@ -521,9 +536,14 @@ public class StreamSpliteratorTest extends OpTestCase {
s -> s.map(i -> i).parallel() s -> s.map(i -> i).parallel()
); );
for (Consumer<DoubleStream> terminalOp : terminalOps) { for (int i = 0; i < terminalOps.size(); i++) {
for (UnaryOperator<DoubleStream> intermediateOp : intermediateOps) { Consumer<DoubleStream> terminalOp = terminalOps.get(i);
for (boolean proxyEstimateSize : new boolean[]{false, true}) { setContext("termOpIndex", i);
for (int j = 0; j < intermediateOps.size(); j++) {
UnaryOperator<DoubleStream> intermediateOp = intermediateOps.get(j);
setContext("intOpIndex", j);
for (boolean proxyEstimateSize : new boolean[] {false, true}) {
setContext("proxyEstimateSize", proxyEstimateSize);
// Size is assumed to be larger than the target size for no splitting // Size is assumed to be larger than the target size for no splitting
// @@@ Need way to obtain the target size // @@@ Need way to obtain the target size
Spliterator.OfDouble sp = intermediateOp.apply(IntStream.range(0, 1000).asDoubleStream()).spliterator(); Spliterator.OfDouble sp = intermediateOp.apply(IntStream.range(0, 1000).asDoubleStream()).spliterator();
......
...@@ -202,26 +202,38 @@ public class TabulatorsTest extends OpTestCase { ...@@ -202,26 +202,38 @@ public class TabulatorsTest extends OpTestCase {
} }
} }
private <T> ResultAsserter<T> mapTabulationAsserter(boolean ordered) {
return (act, exp, ord, par) -> {
if (par & (!ordered || !ord)) {
TabulatorsTest.nestedMapEqualityAssertion(act, exp);
}
else {
LambdaTestHelpers.assertContentsEqual(act, exp);
}
};
}
private<T, M extends Map> private<T, M extends Map>
void exerciseMapTabulation(TestData<T, Stream<T>> data, void exerciseMapTabulation(TestData<T, Stream<T>> data,
Collector<T, ? extends M> collector, Collector<T, ? extends M> collector,
TabulationAssertion<T, M> assertion) TabulationAssertion<T, M> assertion)
throws ReflectiveOperationException { throws ReflectiveOperationException {
boolean ordered = data.isOrdered() boolean ordered = !collector.characteristics().contains(Collector.Characteristics.UNORDERED);
&& !collector.characteristics().contains(Collector.Characteristics.UNORDERED);
M m = withData(data) M m = withData(data)
.terminal(s -> s.collect(collector)) .terminal(s -> s.collect(collector))
.parallelEqualityAsserter(ordered ? LambdaTestHelpers::assertContentsEqual : this::nestedMapEqualityAssertion) .resultAsserter(mapTabulationAsserter(ordered))
.exercise(); .exercise();
assertion.assertValue(m, () -> data.stream(), ordered); assertion.assertValue(m, () -> data.stream(), ordered);
m = withData(data) m = withData(data)
.terminal(s -> s.unordered().collect(collector)) .terminal(s -> s.unordered().collect(collector))
.parallelEqualityAsserter(this::nestedMapEqualityAssertion) .resultAsserter(mapTabulationAsserter(ordered))
.exercise(); .exercise();
assertion.assertValue(m, () -> data.stream(), false); assertion.assertValue(m, () -> data.stream(), false);
} }
private void nestedMapEqualityAssertion(Object o1, Object o2) { private static void nestedMapEqualityAssertion(Object o1, Object o2) {
if (o1 instanceof Map) { if (o1 instanceof Map) {
Map m1 = (Map) o1; Map m1 = (Map) o1;
Map m2 = (Map) o2; Map m2 = (Map) o2;
......
...@@ -29,6 +29,7 @@ import java.util.function.Function; ...@@ -29,6 +29,7 @@ import java.util.function.Function;
import java.util.stream.*; import java.util.stream.*;
import static java.util.stream.LambdaTestHelpers.*; import static java.util.stream.LambdaTestHelpers.*;
import static org.testng.Assert.assertEquals;
/** /**
...@@ -134,15 +135,51 @@ public class ToArrayOpTest extends OpTestCase { ...@@ -134,15 +135,51 @@ public class ToArrayOpTest extends OpTestCase {
s -> s.sorted() s -> s.sorted()
)); ));
private <T extends Object> ResultAsserter<T[]> statefulOpResultAsserter(TestData.OfRef<Integer> data) {
return (act, exp, ord, par) -> {
if (par) {
if (!data.isOrdered()) {
// Relax the checking if the data source is unordered
// It is not exactly possible to determine if the limit
// operation is present and if it is before or after
// the sorted operation
// If the limit operation is present and before the sorted
// operation then the sub-set output after limit is a
// non-deterministic sub-set of the source
List<Integer> expected = new ArrayList<>();
data.forEach(expected::add);
List<T> actual = Arrays.asList(act);
assertEquals(actual.size(), exp.length);
assertTrue(expected.containsAll(actual));
return;
}
else if (!ord) {
LambdaTestHelpers.assertContentsUnordered(Arrays.asList(act),
Arrays.asList(exp));
return;
}
}
assertEquals(act, exp);
};
}
@Test(dataProvider = "StreamTestData<Integer>", dataProviderClass = StreamTestDataProvider.class) @Test(dataProvider = "StreamTestData<Integer>", dataProviderClass = StreamTestDataProvider.class)
public void testStatefulOpPermutations(String name, TestData.OfRef<Integer> data) { public void testStatefulOpPermutations(String name, TestData.OfRef<Integer> data) {
for (Function<Stream<Integer>, Stream<Integer>> f : statefulOpPermutations) { for (Function<Stream<Integer>, Stream<Integer>> f : statefulOpPermutations) {
exerciseTerminalOps(data, f, s -> s.toArray()); withData(data).terminal(f, s -> s.toArray())
.resultAsserter(statefulOpResultAsserter(data))
.exercise();
Integer[] is = exerciseTerminalOps(data, f, s -> s.toArray(Integer[]::new)); Integer[] is = withData(data).terminal(f, s -> s.toArray(Integer[]::new))
.resultAsserter(statefulOpResultAsserter(data))
.exercise();
assertEquals(is.getClass(), Integer[].class); assertEquals(is.getClass(), Integer[].class);
Number[] ns = exerciseTerminalOps(data, f, s -> s.toArray(Number[]::new)); Number[] ns = withData(data).terminal(f, s -> s.toArray(Number[]::new))
.resultAsserter(statefulOpResultAsserter(data))
.exercise();
assertEquals(ns.getClass(), Number[].class); assertEquals(ns.getClass(), Number[].class);
if (data.size() > 0) { if (data.size() > 0) {
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册