1 /*
2 * Copyright (c) 2020, 2026, 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
24 /*
25 * @test
26 * @summary Basic stream tests to iterate on nullable and null-restricted values
27 * @enablePreview
28 * @run junit/othervm StreamTest
29 */
30
31 import jdk.internal.vm.annotation.NullRestricted;
32
33 import java.util.Arrays;
34 import java.util.List;
35 import java.util.stream.Stream;
36
37 import org.junit.jupiter.api.Test;
38 import static org.junit.jupiter.api.Assertions.*;
39
40 public class StreamTest {
41
42 static value class X {
43 int x;
44 X(int x) {
45 this.x = x;
46 }
47 int x() {
48 return x;
49 }
50 }
51
52 static value class Point {
53 public int x;
54 public int y;
55 Point(int x, int y) {
56 this.x = x;
57 this.y = y;
58 }
59 }
60
61 static value class Value {
62 int i;
63 @NullRestricted
64 Point p;
65 Point nullable;
66 List<X> list;
67 Value(int i, Point/* Point! */ p, Point np, List<X> list) {
68 this.i = i;
69 this.p = p;
70 this.nullable = np;
71 this.list = list;
72 }
73
74 Point point() {
75 return p;
76 }
77
78 Point nullablePoint() {
79 return nullable;
80 }
81
82 int getI() { return i; }
83
84 List<X> list() { return list; }
85 }
86
87 final Value[] values = init();
88 private Value[] init() {
89 Value[] values = new Value[10];
90 for (int i = 0; i < 10; i++) {
91 values[i] = new Value(i,
92 new Point(i,i*2),
93 (i%2) == 0 ? null : new Point(i*10, i*20),
94 List.of(new X(i), new X(i*10)));
95 }
96 return values;
97 }
98
99 @Test
100 public void testValues() {
101 Arrays.stream(values)
102 .filter(v -> (v.i % 2) == 0)
103 .forEach(System.out::println);
104 }
105
106 @Test
107 public void testNullRestrictedType() {
108 Arrays.stream(values)
109 .map(Value::point)
110 .filter(p -> p.x >= 5)
111 .forEach(System.out::println);
112
113 }
114
115 @Test
116 public void testNullableValueType() {
117 Arrays.stream(values)
118 .map(Value::nullablePoint)
119 .filter(p -> p != null)
120 .forEach(System.out::println);
121 }
122
123 @Test
124 public void mapToInt() {
125 Stream<Point> stream = Arrays.stream(values)
126 .filter(v -> (v.getI() % 2) == 0)
127 .map(Value::point);
128 stream.forEach(p -> assertTrue((p.x % 2) == 0));
129 }
130
131 @Test
132 public void testListOfValues() {
133 long count = Arrays.stream(values)
134 .map(Value::list)
135 .flatMap(List::stream)
136 .map(X::x)
137 .filter(x -> x >= 10)
138 .count();
139 assertEquals(count, values.length-1);
140 }
141 }