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 java.util.stream;
  24 
  25 import org.testng.annotations.DataProvider;
  26 import org.testng.annotations.Test;
  27 
  28 import java.util.*;
  29 import java.util.function.DoubleConsumer;
  30 import java.util.function.IntConsumer;
  31 import java.util.function.LongConsumer;
  32 
  33 import static org.testng.Assert.assertEquals;
  34 import static org.testng.Assert.assertFalse;
  35 
  36 @Test
  37 public class SpinedBufferTest {
  38 
  39     // Create sizes around the boundary of spines
  40     static List<Integer> sizes;
  41     static {
  42         try {
  43             sizes = IntStream.range(0, 15)
  44                              .map(i -> 1 << i)
  45                              .flatMap(i -> Arrays.stream(new int[] { i-2, i-1, i, i+1, i+2 }))
  46                              .filter(i -> i >= 0)
  47                              .boxed()
  48                              .distinct()
  49                              .collect(Collectors.toList());
  50         }
  51         catch (Exception e) {
  52             e.printStackTrace();
  53         }
  54     }
  55 
  56     private static final int TEST_SIZE = 5000;
  57 
  58     // SpinedBuffer
  59 
  60     @DataProvider(name = "SpinedBuffer")
  61     public Object[][] createSpinedBuffer() {
  62         List<Object[]> params = new ArrayList<>();
  63 
  64         for (int size : sizes) {
  65             int[] array = IntStream.range(0, size).toArray();
  66 
  67             SpinedBuffer<Integer> sb = new SpinedBuffer<>();
  68             Arrays.stream(array).boxed().forEach(sb);
  69             params.add(new Object[]{array, sb});
  70 
  71             sb = new SpinedBuffer<>(size / 2);
  72             Arrays.stream(array).boxed().forEach(sb);
  73             params.add(new Object[]{array, sb});
  74 
  75             sb = new SpinedBuffer<>(size);
  76             Arrays.stream(array).boxed().forEach(sb);
  77             params.add(new Object[]{array, sb});
  78 
  79             sb = new SpinedBuffer<>(size * 2);
  80             Arrays.stream(array).boxed().forEach(sb);
  81             params.add(new Object[]{array, sb});
  82         }
  83 
  84         return params.toArray(new Object[0][]);
  85     }
  86 
  87     @Test(dataProvider = "SpinedBuffer")
  88     public void testSpliterator(int[] array, SpinedBuffer<Integer> sb) {
  89         assertEquals(sb.count(), array.length);
  90         assertEquals(sb.count(), sb.spliterator().getExactSizeIfKnown());
  91 
  92         SpliteratorTestHelper.testSpliterator(sb::spliterator);
  93     }
  94 
  95     @Test(dataProvider = "SpinedBuffer", groups = { "serialization-hostile" })
  96     public void testLastSplit(int[] array, SpinedBuffer<Integer> sb) {
  97         Spliterator<Integer> spliterator = sb.spliterator();
  98         Spliterator<Integer> split = spliterator.trySplit();
  99         long splitSizes = (split == null) ? 0 : split.getExactSizeIfKnown();
 100         long lastSplitSize = spliterator.getExactSizeIfKnown();
 101         splitSizes += lastSplitSize;
 102 
 103         assertEquals(splitSizes, array.length);
 104 
 105         List<Integer> contentOfLastSplit = new ArrayList<>();
 106         spliterator.forEachRemaining(contentOfLastSplit::add);
 107 
 108         assertEquals(contentOfLastSplit.size(), lastSplitSize);
 109 
 110         List<Integer> end = Arrays.stream(array)
 111                 .boxed()
 112                 .substream(array.length - lastSplitSize)
 113                 .collect(Collectors.toList());
 114         assertEquals(contentOfLastSplit, end);
 115     }
 116 
 117     @Test(groups = { "serialization-hostile" })
 118     public void testSpinedBuffer() {
 119         List<Integer> list1 = new ArrayList<>();
 120         List<Integer> list2 = new ArrayList<>();
 121         SpinedBuffer<Integer> sb = new SpinedBuffer<>();
 122         for (int i = 0; i < TEST_SIZE; i++) {
 123             list1.add(i);
 124             sb.accept(i);
 125         }
 126         Iterator<Integer> it = sb.iterator();
 127         for (int i = 0; i < TEST_SIZE; i++)
 128             list2.add(it.next());
 129         assertFalse(it.hasNext());
 130         assertEquals(list1, list2);
 131 
 132         for (int i = 0; i < TEST_SIZE; i++)
 133             assertEquals(sb.get(i), (Integer) i, Integer.toString(i));
 134 
 135         list2.clear();
 136         sb.forEach(list2::add);
 137         assertEquals(list1, list2);
 138         Integer[] array = sb.asArray(LambdaTestHelpers.integerArrayGenerator);
 139         list2.clear();
 140         for (Integer i : array)
 141             list2.add(i);
 142         assertEquals(list1, list2);
 143     }
 144 
 145     // IntSpinedBuffer
 146 
 147     @DataProvider(name = "IntSpinedBuffer")
 148     public Object[][] createIntSpinedBuffer() {
 149         List<Object[]> params = new ArrayList<>();
 150 
 151         for (int size : sizes) {
 152             int[] array = IntStream.range(0, size).toArray();
 153             SpinedBuffer.OfInt sb = new SpinedBuffer.OfInt();
 154             Arrays.stream(array).forEach(sb);
 155 
 156             params.add(new Object[]{array, sb});
 157         }
 158 
 159         return params.toArray(new Object[0][]);
 160     }
 161 
 162     @Test(dataProvider = "IntSpinedBuffer")
 163     public void testIntSpliterator(int[] array, SpinedBuffer.OfInt sb) {
 164         assertEquals(sb.count(), array.length);
 165         assertEquals(sb.count(), sb.spliterator().getExactSizeIfKnown());
 166 
 167         SpliteratorTestHelper.testIntSpliterator(sb::spliterator);
 168     }
 169 
 170     @Test(dataProvider = "IntSpinedBuffer", groups = { "serialization-hostile" })
 171     public void testIntLastSplit(int[] array, SpinedBuffer.OfInt sb) {
 172         Spliterator.OfInt spliterator = sb.spliterator();
 173         Spliterator.OfInt split = spliterator.trySplit();
 174         long splitSizes = (split == null) ? 0 : split.getExactSizeIfKnown();
 175         long lastSplitSize = spliterator.getExactSizeIfKnown();
 176         splitSizes += lastSplitSize;
 177 
 178         assertEquals(splitSizes, array.length);
 179 
 180         List<Integer> contentOfLastSplit = new ArrayList<>();
 181         spliterator.forEachRemaining((IntConsumer) contentOfLastSplit::add);
 182 
 183         assertEquals(contentOfLastSplit.size(), lastSplitSize);
 184 
 185         List<Integer> end = Arrays.stream(array)
 186                 .boxed()
 187                 .substream(array.length - lastSplitSize)
 188                 .collect(Collectors.toList());
 189         assertEquals(contentOfLastSplit, end);
 190     }
 191 
 192     @Test(groups = { "serialization-hostile" })
 193     public void testIntSpinedBuffer() {
 194         List<Integer> list1 = new ArrayList<>();
 195         List<Integer> list2 = new ArrayList<>();
 196         SpinedBuffer.OfInt sb = new SpinedBuffer.OfInt();
 197         for (int i = 0; i < TEST_SIZE; i++) {
 198             list1.add(i);
 199             sb.accept(i);
 200         }
 201         PrimitiveIterator.OfInt it = sb.iterator();
 202         for (int i = 0; i < TEST_SIZE; i++)
 203             list2.add(it.nextInt());
 204         assertFalse(it.hasNext());
 205         assertEquals(list1, list2);
 206 
 207         for (int i = 0; i < TEST_SIZE; i++)
 208             assertEquals(sb.get(i), i, Integer.toString(i));
 209 
 210         list2.clear();
 211         sb.forEach((int i) -> list2.add(i));
 212         assertEquals(list1, list2);
 213         int[] array = sb.asPrimitiveArray();
 214         list2.clear();
 215         for (int i : array)
 216             list2.add(i);
 217         assertEquals(list1, list2);
 218     }
 219 
 220     // LongSpinedBuffer
 221 
 222     @DataProvider(name = "LongSpinedBuffer")
 223     public Object[][] createLongSpinedBuffer() {
 224         List<Object[]> params = new ArrayList<>();
 225 
 226         for (int size : sizes) {
 227             long[] array = LongStream.range(0, size).toArray();
 228             SpinedBuffer.OfLong sb = new SpinedBuffer.OfLong();
 229             Arrays.stream(array).forEach(sb);
 230 
 231             params.add(new Object[]{array, sb});
 232         }
 233 
 234         return params.toArray(new Object[0][]);
 235     }
 236 
 237     @Test(dataProvider = "LongSpinedBuffer")
 238     public void testLongSpliterator(long[] array, SpinedBuffer.OfLong sb) {
 239         assertEquals(sb.count(), array.length);
 240         assertEquals(sb.count(), sb.spliterator().getExactSizeIfKnown());
 241 
 242         SpliteratorTestHelper.testLongSpliterator(sb::spliterator);
 243     }
 244 
 245     @Test(dataProvider = "LongSpinedBuffer", groups = { "serialization-hostile" })
 246     public void testLongLastSplit(long[] array, SpinedBuffer.OfLong sb) {
 247         Spliterator.OfLong spliterator = sb.spliterator();
 248         Spliterator.OfLong split = spliterator.trySplit();
 249         long splitSizes = (split == null) ? 0 : split.getExactSizeIfKnown();
 250         long lastSplitSize = spliterator.getExactSizeIfKnown();
 251         splitSizes += lastSplitSize;
 252 
 253         assertEquals(splitSizes, array.length);
 254 
 255         List<Long> contentOfLastSplit = new ArrayList<>();
 256         spliterator.forEachRemaining((LongConsumer) contentOfLastSplit::add);
 257 
 258         assertEquals(contentOfLastSplit.size(), lastSplitSize);
 259 
 260         List<Long> end = Arrays.stream(array)
 261                 .boxed()
 262                 .substream(array.length - lastSplitSize)
 263                 .collect(Collectors.toList());
 264         assertEquals(contentOfLastSplit, end);
 265     }
 266 
 267     @Test(groups = { "serialization-hostile" })
 268     public void testLongSpinedBuffer() {
 269         List<Long> list1 = new ArrayList<>();
 270         List<Long> list2 = new ArrayList<>();
 271         SpinedBuffer.OfLong sb = new SpinedBuffer.OfLong();
 272         for (long i = 0; i < TEST_SIZE; i++) {
 273             list1.add(i);
 274             sb.accept(i);
 275         }
 276         PrimitiveIterator.OfLong it = sb.iterator();
 277         for (int i = 0; i < TEST_SIZE; i++)
 278             list2.add(it.nextLong());
 279         assertFalse(it.hasNext());
 280         assertEquals(list1, list2);
 281 
 282         for (int i = 0; i < TEST_SIZE; i++)
 283             assertEquals(sb.get(i), i, Long.toString(i));
 284 
 285         list2.clear();
 286         sb.forEach((long i) -> list2.add(i));
 287         assertEquals(list1, list2);
 288         long[] array = sb.asPrimitiveArray();
 289         list2.clear();
 290         for (long i : array)
 291             list2.add(i);
 292         assertEquals(list1, list2);
 293     }
 294 
 295     // DoubleSpinedBuffer
 296 
 297     @DataProvider(name = "DoubleSpinedBuffer")
 298     public Object[][] createDoubleSpinedBuffer() {
 299         List<Object[]> params = new ArrayList<>();
 300 
 301         for (int size : sizes) {
 302             // @@@ replace with double range when implemented
 303             double[] array = LongStream.range(0, size).asDoubleStream().toArray();
 304             SpinedBuffer.OfDouble sb = new SpinedBuffer.OfDouble();
 305             Arrays.stream(array).forEach(sb);
 306 
 307             params.add(new Object[]{array, sb});
 308         }
 309 
 310         return params.toArray(new Object[0][]);
 311     }
 312 
 313     @Test(dataProvider = "DoubleSpinedBuffer")
 314     public void testDoubleSpliterator(double[] array, SpinedBuffer.OfDouble sb) {
 315         assertEquals(sb.count(), array.length);
 316         assertEquals(sb.count(), sb.spliterator().getExactSizeIfKnown());
 317 
 318         SpliteratorTestHelper.testDoubleSpliterator(sb::spliterator);
 319     }
 320 
 321     @Test(dataProvider = "DoubleSpinedBuffer", groups = { "serialization-hostile" })
 322     public void testLongLastSplit(double[] array, SpinedBuffer.OfDouble sb) {
 323         Spliterator.OfDouble spliterator = sb.spliterator();
 324         Spliterator.OfDouble split = spliterator.trySplit();
 325         long splitSizes = (split == null) ? 0 : split.getExactSizeIfKnown();
 326         long lastSplitSize = spliterator.getExactSizeIfKnown();
 327         splitSizes += lastSplitSize;
 328 
 329         assertEquals(splitSizes, array.length);
 330 
 331         List<Double> contentOfLastSplit = new ArrayList<>();
 332         spliterator.forEachRemaining((DoubleConsumer) contentOfLastSplit::add);
 333 
 334         assertEquals(contentOfLastSplit.size(), lastSplitSize);
 335 
 336         List<Double> end = Arrays.stream(array)
 337                 .boxed()
 338                 .substream(array.length - lastSplitSize)
 339                 .collect(Collectors.toList());
 340         assertEquals(contentOfLastSplit, end);
 341     }
 342 
 343     @Test(groups = { "serialization-hostile" })
 344     public void testDoubleSpinedBuffer() {
 345         List<Double> list1 = new ArrayList<>();
 346         List<Double> list2 = new ArrayList<>();
 347         SpinedBuffer.OfDouble sb = new SpinedBuffer.OfDouble();
 348         for (long i = 0; i < TEST_SIZE; i++) {
 349             list1.add((double) i);
 350             sb.accept((double) i);
 351         }
 352         PrimitiveIterator.OfDouble it = sb.iterator();
 353         for (int i = 0; i < TEST_SIZE; i++)
 354             list2.add(it.nextDouble());
 355         assertFalse(it.hasNext());
 356         assertEquals(list1, list2);
 357 
 358         for (int i = 0; i < TEST_SIZE; i++)
 359             assertEquals(sb.get(i), (double) i, Double.toString(i));
 360 
 361         list2.clear();
 362         sb.forEach((double i) -> list2.add(i));
 363         assertEquals(list1, list2);
 364         double[] array = sb.asPrimitiveArray();
 365         list2.clear();
 366         for (double i : array)
 367             list2.add(i);
 368         assertEquals(list1, list2);
 369     }
 370 }