1 /*
   2  * Copyright (c) 2012, 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.tests.java.util.stream;
  24 
  25 import java.util.Arrays;
  26 import java.util.Optional;
  27 import java.util.Spliterator;
  28 import java.util.stream.IntStream;
  29 import java.util.stream.LongStream;
  30 import java.util.stream.OpTestCase;
  31 import java.util.stream.SpliteratorTestHelper;
  32 import java.util.stream.Stream;
  33 import java.util.stream.TestData;
  34 
  35 import org.testng.annotations.Test;
  36 
  37 /**
  38  * Primitive range tests
  39  *
  40  * @author Brian Goetz
  41  */
  42 @Test
  43 public class RangeTest extends OpTestCase {
  44 
  45     public void testInfiniteRangeFindFirst() {
  46         Integer first = Stream.iterate(0, i -> i + 1).filter(i -> i > 10000).findFirst().get();
  47         assertEquals(first, Stream.iterate(0, i -> i + 1).parallel().filter(i -> i > 10000).findFirst().get());
  48 
  49         // Limit is required to transform the infinite stream to a finite stream
  50         // since the exercising requires a finite stream
  51         withData(TestData.Factory.ofSupplier(
  52                 "", () -> Stream.iterate(0, i -> i + 1).filter(i -> i > 10000).limit(20000))).
  53                 terminal(s->s.findFirst()).expectedResult(Optional.of(10001)).exercise();
  54     }
  55 
  56     //
  57 
  58     public void testIntRange() {
  59         // Half-open
  60         for (int start : Arrays.asList(1, 10, -1, -10)) {
  61             setContext("start", start);
  62             for (int end : Arrays.asList(1, 10, -1, -10)) {
  63                 setContext("end", end);
  64                 int size = (start < end) ? end - start : 0;
  65                 int[] exp = new int[size];
  66                 for (int i = start, p = 0; i < end; i++, p++) {
  67                     exp[p] = i;
  68                 }
  69 
  70                 int[] inc = IntStream.range(start, end).toArray();
  71                 assertEquals(inc.length, size);
  72                 assertTrue(Arrays.equals(exp, inc));
  73 
  74                 withData(intRangeData(start, end)).stream(s -> s).
  75                         expectedResult(exp).exercise();
  76             }
  77         }
  78 
  79         // Closed
  80         for (int start : Arrays.asList(1, 10, -1, -10)) {
  81             setContext("start", start);
  82             for (int end : Arrays.asList(1, 10, -1, -10)) {
  83                 setContext("end", end);
  84                 int size = (start <= end) ? end - start + 1 : 0;
  85                 int[] exp = new int[size];
  86                 for (int i = start, p = 0; i <= end; i++, p++) {
  87                     exp[p] = i;
  88                 }
  89 
  90                 int[] inc = IntStream.rangeClosed(start, end).toArray();
  91                 assertEquals(inc.length, size);
  92                 assertTrue(Arrays.equals(exp, inc));
  93 
  94                 withData(intRangeClosedData(start, end)).stream(s -> s).
  95                         expectedResult(exp).exercise();
  96             }
  97         }
  98 
  99         // Closed, maximum upper bound of Integer.MAX_VALUE
 100         {
 101             int[] inc = IntStream.rangeClosed(Integer.MAX_VALUE - 1, Integer.MAX_VALUE).toArray();
 102             assertEquals(2, inc.length);
 103             assertEquals(Integer.MAX_VALUE - 1, inc[0]);
 104             assertEquals(Integer.MAX_VALUE, inc[1]);
 105 
 106             inc = IntStream.rangeClosed(Integer.MAX_VALUE, Integer.MAX_VALUE).toArray();
 107             assertEquals(1, inc.length);
 108             assertEquals(Integer.MAX_VALUE, inc[0]);
 109 
 110             SpliteratorTestHelper.testIntSpliterator(
 111                     () -> IntStream.rangeClosed(Integer.MAX_VALUE - 8, Integer.MAX_VALUE).spliterator());
 112         }
 113 
 114         // Range wider than Integer.MAX_VALUE
 115         {
 116             Spliterator.OfInt s = IntStream.rangeClosed(Integer.MIN_VALUE, Integer.MAX_VALUE).
 117                     spliterator();
 118             assertEquals(s.estimateSize(), 1L << 32);
 119         }
 120     }
 121 
 122     TestData.OfInt intRangeData(int start, int end) {
 123         return TestData.Factory.ofIntSupplier("int range", () -> IntStream.range(start, end));
 124     }
 125 
 126     TestData.OfInt intRangeClosedData(int start, int end) {
 127         return TestData.Factory.ofIntSupplier("int rangeClosed", () -> IntStream.rangeClosed(start, end));
 128     }
 129 
 130     public void tesIntRangeReduce() {
 131         withData(intRangeData(0, 10000)).
 132                 terminal(s -> s.reduce(0, Integer::sum)).exercise();
 133     }
 134 
 135     public void testIntInfiniteRangeLimit() {
 136         withData(TestData.Factory.ofIntSupplier(
 137                 "int range", () -> IntStream.iterate(0, i -> i + 1).limit(10000))).
 138                 terminal(s -> s.reduce(0, Integer::sum)).exercise();
 139     }
 140 
 141     public void testIntInfiniteRangeFindFirst() {
 142         int first = IntStream.iterate(0, i -> i + 1).filter(i -> i > 10000).findFirst().getAsInt();
 143         assertEquals(first, IntStream.iterate(0, i -> i + 1).parallel().filter(i -> i > 10000).findFirst().getAsInt());
 144     }
 145 
 146     //
 147 
 148     public void testLongRange() {
 149         // Half-open
 150         for (long start : Arrays.asList(1, 1000, -1, -1000)) {
 151             setContext("start", start);
 152             for (long end : Arrays.asList(1, 1000, -1, -1000)) {
 153                 setContext("end", end);
 154                 long size = start < end ? end - start : 0;
 155                 long[] exp = new long[(int) size];
 156                 for (long i = start, p = 0; i < end; i++, p++) {
 157                     exp[(int) p] = i;
 158                 }
 159 
 160                 long[] inc = LongStream.range(start, end).toArray();
 161                 assertEquals(inc.length, size);
 162                 assertTrue(Arrays.equals(exp, inc));
 163 
 164                 withData(longRangeData(start, end)).stream(s -> s).
 165                         expectedResult(exp).exercise();
 166             }
 167         }
 168 
 169         // Closed
 170         for (long start : Arrays.asList(1, 1000, -1, -1000)) {
 171             setContext("start", start);
 172             for (long end : Arrays.asList(1, 1000, -1, -1000)) {
 173                 setContext("end", end);
 174                 long size = start <= end ? end - start + 1: 0;
 175                 long[] exp = new long[(int) size];
 176                 for (long i = start, p = 0; i <= end; i++, p++) {
 177                     exp[(int) p] = i;
 178                 }
 179 
 180                 long[] inc = LongStream.rangeClosed(start, end).toArray();
 181                 assertEquals(inc.length, size);
 182                 assertTrue(Arrays.equals(exp, inc));
 183 
 184                 withData(longRangeClosedData(start, end)).stream(s -> s).
 185                         expectedResult(exp).exercise();
 186             }
 187         }
 188 
 189         // Closed, maximum upper bound of Long.MAX_VALUE
 190         {
 191             long[] inc = LongStream.rangeClosed(Long.MAX_VALUE - 1, Long.MAX_VALUE).toArray();
 192             assertEquals(2, inc.length);
 193             assertEquals(Long.MAX_VALUE - 1, inc[0]);
 194             assertEquals(Long.MAX_VALUE, inc[1]);
 195 
 196             inc = LongStream.rangeClosed(Long.MAX_VALUE, Long.MAX_VALUE).toArray();
 197             assertEquals(1, inc.length);
 198             assertEquals(Long.MAX_VALUE, inc[0]);
 199 
 200             SpliteratorTestHelper.testLongSpliterator(
 201                     () -> LongStream.rangeClosed(Long.MAX_VALUE - 8, Long.MAX_VALUE).spliterator());
 202         }
 203     }
 204 
 205     TestData.OfLong longRangeData(long start, long end) {
 206         return TestData.Factory.ofLongSupplier("long range", () -> LongStream.range(start, end));
 207     }
 208 
 209     TestData.OfLong longRangeClosedData(long start, long end) {
 210         return TestData.Factory.ofLongSupplier("long rangeClosed", () -> LongStream.rangeClosed(start, end));
 211     }
 212 
 213     public void testLongRangeReduce() {
 214         withData(longRangeData(0, 10000)).
 215                 terminal(s -> s.reduce(0, Long::sum)).exercise();
 216     }
 217 
 218     public void testLongInfiniteRangeLimit() {
 219         withData(TestData.Factory.ofLongSupplier(
 220                 "long range", () -> LongStream.iterate(0, i -> i + 1).limit(10000))).
 221                 terminal(s -> s.reduce(0, Long::sum)).exercise();
 222     }
 223 
 224     public void testLongInfiniteRangeFindFirst() {
 225         long first = LongStream.iterate(0, i -> i + 1).filter(i -> i > 10000).findFirst().getAsLong();
 226         assertEquals(first, LongStream.iterate(0, i -> i + 1).parallel().filter(i -> i > 10000).findFirst().getAsLong());
 227     }
 228 
 229     // Enable when Stream.concat is present and range implementations are
 230     // updated to use that
 231 //    private static void assertSizedAndSubSized(Spliterator<?> s) {
 232 //        assertTrue(s.hasCharacteristics(Spliterator.SIZED | Spliterator.SUBSIZED));
 233 //    }
 234 //
 235 //    private static void assertNotSizedAndSubSized(Spliterator<?> s) {
 236 //        assertFalse(s.hasCharacteristics(Spliterator.SIZED | Spliterator.SUBSIZED));
 237 //    }
 238 //
 239 //    public void testLongLongRange() {
 240 //        // Test [Long.MIN_VALUE, Long.MAX_VALUE)
 241 //        // This will concatenate streams of three ranges
 242 //        //   [Long.MIN_VALUE, x) [x, 0) [0, Long.MAX_VALUE)
 243 //        // where x = Long.divideUnsigned(0 - Long.MIN_VALUE, 2) + 1
 244 //        {
 245 //            Spliterator.OfLong s = LongStream.range(Long.MIN_VALUE, Long.MAX_VALUE).spliterator();
 246 //
 247 //            assertEquals(s.estimateSize(), Long.MAX_VALUE);
 248 //            assertNotSizedAndSubSized(s);
 249 //
 250 //            Spliterator.OfLong s1 = s.trySplit();
 251 //            assertNotSizedAndSubSized(s1);
 252 //            assertSizedAndSubSized(s);
 253 //
 254 //            Spliterator.OfLong s2 = s1.trySplit();
 255 //            assertSizedAndSubSized(s1);
 256 //            assertSizedAndSubSized(s2);
 257 //
 258 //            assertTrue(s.estimateSize() == Long.MAX_VALUE);
 259 //            assertTrue(s1.estimateSize() < Long.MAX_VALUE);
 260 //            assertTrue(s2.estimateSize() < Long.MAX_VALUE);
 261 //
 262 //            assertEquals(s.estimateSize() + s1.estimateSize() + s2.estimateSize(),
 263 //                         Long.MAX_VALUE - Long.MIN_VALUE);
 264 //        }
 265 //
 266 //        long[][] ranges = { {Long.MIN_VALUE, 0}, {-1, Long.MAX_VALUE} };
 267 //        for (int i = 0; i < ranges.length; i++) {
 268 //            long start = ranges[i][0];
 269 //            long end = ranges[i][1];
 270 //
 271 //            Spliterator.OfLong s = LongStream.range(start, end).spliterator();
 272 //
 273 //            assertEquals(s.estimateSize(), Long.MAX_VALUE);
 274 //            assertNotSizedAndSubSized(s);
 275 //
 276 //            Spliterator.OfLong s1 = s.trySplit();
 277 //            assertSizedAndSubSized(s1);
 278 //            assertSizedAndSubSized(s);
 279 //
 280 //            assertTrue(s.estimateSize() < Long.MAX_VALUE);
 281 //            assertTrue(s1.estimateSize() < Long.MAX_VALUE);
 282 //
 283 //            assertEquals(s.estimateSize() + s1.estimateSize(), end - start);
 284 //        }
 285 //    }
 286 //
 287 //    public void testLongLongRangeClosed() {
 288 //        // Test [Long.MIN_VALUE, Long.MAX_VALUE]
 289 //        // This will concatenate streams of four ranges
 290 //        //   [Long.MIN_VALUE, x) [x, 0) [0, y) [y, Long.MAX_VALUE]
 291 //        // where x = Long.divideUnsigned(0 - Long.MIN_VALUE, 2) + 1
 292 //        //       y = Long.divideUnsigned(Long.MAX_VALUE, 2) + 1
 293 //
 294 //        {
 295 //            Spliterator.OfLong s = LongStream.rangeClosed(Long.MIN_VALUE, Long.MAX_VALUE).spliterator();
 296 //
 297 //            assertEquals(s.estimateSize(), Long.MAX_VALUE);
 298 //            assertNotSizedAndSubSized(s);
 299 //
 300 //            Spliterator.OfLong s1 = s.trySplit();
 301 //            assertNotSizedAndSubSized(s1);
 302 //            assertNotSizedAndSubSized(s);
 303 //
 304 //            Spliterator.OfLong s2 = s1.trySplit();
 305 //            assertSizedAndSubSized(s1);
 306 //            assertSizedAndSubSized(s2);
 307 //
 308 //            Spliterator.OfLong s3 = s.trySplit();
 309 //            assertSizedAndSubSized(s3);
 310 //            assertSizedAndSubSized(s);
 311 //
 312 //            assertTrue(s.estimateSize() < Long.MAX_VALUE);
 313 //            assertTrue(s3.estimateSize() < Long.MAX_VALUE);
 314 //            assertTrue(s1.estimateSize() < Long.MAX_VALUE);
 315 //            assertTrue(s2.estimateSize() < Long.MAX_VALUE);
 316 //
 317 //            assertEquals(s.estimateSize() + s3.estimateSize() + s1.estimateSize() + s2.estimateSize(),
 318 //                         Long.MAX_VALUE - Long.MIN_VALUE + 1);
 319 //        }
 320 //
 321 //        long[][] ranges = { {Long.MIN_VALUE, 0}, {-1, Long.MAX_VALUE} };
 322 //        for (int i = 0; i < ranges.length; i++) {
 323 //            long start = ranges[i][0];
 324 //            long end = ranges[i][1];
 325 //
 326 //            Spliterator.OfLong s = LongStream.rangeClosed(start, end).spliterator();
 327 //
 328 //            assertEquals(s.estimateSize(), Long.MAX_VALUE);
 329 //            assertNotSizedAndSubSized(s);
 330 //
 331 //            Spliterator.OfLong s1 = s.trySplit();
 332 //            assertSizedAndSubSized(s1);
 333 //            assertSizedAndSubSized(s);
 334 //
 335 //            assertTrue(s.estimateSize() < Long.MAX_VALUE);
 336 //            assertTrue(s1.estimateSize() < Long.MAX_VALUE);
 337 //
 338 //            assertEquals(s.estimateSize() + s1.estimateSize(), end - start + 1);
 339 //        }
 340 //    }
 341 }