Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
PojavLauncherTeam
GitHub Repository: PojavLauncherTeam/mobile
Path: blob/master/test/jdk/java/util/Collection/MOAT.java
41152 views
1
/*
2
* Copyright (c) 2005, 2020, 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
* @bug 6207984 6272521 6192552 6269713 6197726 6260652 5073546 4137464
27
* 4155650 4216399 4294891 6282555 6318622 6355327 6383475 6420753
28
* 6431845 4802633 6570566 6570575 6570631 6570924 6691185 6691215
29
* 4802647 7123424 8024709 8193128
30
* @summary Run many tests on many Collection and Map implementations
31
* @author Martin Buchholz
32
* @modules java.base/java.util:open
33
* @run main MOAT
34
* @key randomness
35
*/
36
37
/* Mother Of All (Collection) Tests
38
*
39
* Testing of collection classes is often spotty, because many tests
40
* need to be performed on many implementations, but the onus on
41
* writing the tests falls on the engineer introducing the new
42
* implementation.
43
*
44
* The idea of this mega-test is that:
45
*
46
* An engineer adding a new collection implementation could simply add
47
* their new implementation to a list of implementations in this
48
* test's main method. Any general purpose Collection<Integer> or
49
* Map<Integer,Integer> class is appropriate.
50
*
51
* An engineer fixing a regression could add their regression test here and
52
* simultaneously test all other implementations.
53
*/
54
55
import java.io.*;
56
import java.util.*;
57
import java.util.concurrent.*;
58
import static java.util.Collections.*;
59
import java.lang.reflect.*;
60
import java.util.stream.Collectors;
61
import java.util.stream.Stream;
62
63
public class MOAT {
64
// Collections under test must not be initialized to contain this value,
65
// and maps under test must not contain this value as a key.
66
// It's used as a sentinel for absent-element testing.
67
static final int ABSENT_VALUE = 778347983;
68
69
static final Integer[] integerArray;
70
static {
71
Integer[] ia = new Integer[20];
72
// fill with 1..20 inclusive
73
for (int i = 0; i < ia.length; i++) {
74
ia[i] = i + 1;
75
}
76
integerArray = ia;
77
}
78
79
public static void realMain(String[] args) {
80
81
testCollection(new NewAbstractCollection<Integer>());
82
testCollection(new NewAbstractSet<Integer>());
83
testCollection(new LinkedHashSet<Integer>());
84
testCollection(new HashSet<Integer>());
85
testCollection(new Vector<Integer>());
86
testCollection(new Vector<Integer>().subList(0,0));
87
testCollection(new ArrayDeque<Integer>());
88
testCollection(new ArrayList<Integer>());
89
testCollection(new ArrayList<Integer>().subList(0,0));
90
testCollection(new LinkedList<Integer>());
91
testCollection(new LinkedList<Integer>().subList(0,0));
92
testCollection(new TreeSet<Integer>());
93
testCollection(Collections.checkedList(new ArrayList<Integer>(), Integer.class));
94
testCollection(Collections.synchronizedList(new ArrayList<Integer>()));
95
testCollection(Collections.checkedSet(new HashSet<Integer>(), Integer.class));
96
testCollection(Collections.checkedSortedSet(new TreeSet<Integer>(), Integer.class));
97
testCollection(Collections.checkedNavigableSet(new TreeSet<Integer>(), Integer.class));
98
testCollection(Collections.synchronizedSet(new HashSet<Integer>()));
99
testCollection(Collections.synchronizedSortedSet(new TreeSet<Integer>()));
100
testCollection(Collections.synchronizedNavigableSet(new TreeSet<Integer>()));
101
102
testCollection(new CopyOnWriteArrayList<Integer>());
103
testCollection(new CopyOnWriteArrayList<Integer>().subList(0,0));
104
testCollection(new CopyOnWriteArraySet<Integer>());
105
testCollection(new PriorityQueue<Integer>());
106
testCollection(new PriorityBlockingQueue<Integer>());
107
testCollection(new ArrayBlockingQueue<Integer>(20));
108
testCollection(new LinkedBlockingQueue<Integer>(20));
109
testCollection(new LinkedBlockingDeque<Integer>(20));
110
testCollection(new ConcurrentLinkedDeque<Integer>());
111
testCollection(new ConcurrentLinkedQueue<Integer>());
112
testCollection(new LinkedTransferQueue<Integer>());
113
testCollection(new ConcurrentSkipListSet<Integer>());
114
testCollection(Arrays.asList(new Integer(42)));
115
testCollection(Arrays.asList(1,2,3));
116
testCollection(nCopies(25,1));
117
testImmutableList(nCopies(25,1));
118
119
testMap(new HashMap<Integer,Integer>());
120
testMap(new LinkedHashMap<Integer,Integer>());
121
122
// TODO: Add reliable support for WeakHashMap.
123
// This test is subject to very rare failures because the GC
124
// may remove unreferenced-keys from the map at any time.
125
// testMap(new WeakHashMap<Integer,Integer>());
126
127
testMap(new IdentityHashMap<Integer,Integer>());
128
testMap(new TreeMap<Integer,Integer>());
129
testMap(new Hashtable<Integer,Integer>());
130
testMap(new ConcurrentHashMap<Integer,Integer>(10, 0.5f));
131
testMap(new ConcurrentSkipListMap<Integer,Integer>());
132
testMap(Collections.checkedMap(new HashMap<Integer,Integer>(), Integer.class, Integer.class));
133
testMap(Collections.checkedSortedMap(new TreeMap<Integer,Integer>(), Integer.class, Integer.class));
134
testMap(Collections.checkedNavigableMap(new TreeMap<Integer,Integer>(), Integer.class, Integer.class));
135
testMap(Collections.synchronizedMap(new HashMap<Integer,Integer>()));
136
testMap(Collections.synchronizedSortedMap(new TreeMap<Integer,Integer>()));
137
testMap(Collections.synchronizedNavigableMap(new TreeMap<Integer,Integer>()));
138
139
// Unmodifiable wrappers
140
testImmutableSet(unmodifiableSet(new HashSet<>(Arrays.asList(1,2,3))));
141
testImmutableList(unmodifiableList(Arrays.asList(1,2,3)));
142
testImmutableMap(unmodifiableMap(Collections.singletonMap(1,2)));
143
testCollMutatorsAlwaysThrow(unmodifiableSet(new HashSet<>(Arrays.asList(1,2,3))));
144
testCollMutatorsAlwaysThrow(unmodifiableSet(Collections.emptySet()));
145
testEmptyCollMutatorsAlwaysThrow(unmodifiableSet(Collections.emptySet()));
146
testListMutatorsAlwaysThrow(unmodifiableList(Arrays.asList(1,2,3)));
147
testListMutatorsAlwaysThrow(unmodifiableList(Collections.emptyList()));
148
testEmptyListMutatorsAlwaysThrow(unmodifiableList(Collections.emptyList()));
149
testMapMutatorsAlwaysThrow(unmodifiableMap(Collections.singletonMap(1,2)));
150
testMapMutatorsAlwaysThrow(unmodifiableMap(Collections.emptyMap()));
151
testEmptyMapMutatorsAlwaysThrow(unmodifiableMap(Collections.emptyMap()));
152
153
// Empty collections
154
final List<Integer> emptyArray = Arrays.asList(new Integer[]{});
155
testCollection(emptyArray);
156
testEmptyList(emptyArray);
157
THROWS(IndexOutOfBoundsException.class, () -> emptyArray.set(0,1));
158
THROWS(UnsupportedOperationException.class, () -> emptyArray.add(0,1));
159
160
List<Integer> noOne = nCopies(0,1);
161
testCollection(noOne);
162
testEmptyList(noOne);
163
testImmutableList(noOne);
164
165
Set<Integer> emptySet = emptySet();
166
testCollection(emptySet);
167
testEmptySet(emptySet);
168
testEmptySet(EMPTY_SET);
169
testEmptySet(Collections.emptySet());
170
testEmptySet(Collections.emptySortedSet());
171
testEmptySet(Collections.emptyNavigableSet());
172
testImmutableSet(emptySet);
173
174
List<Integer> emptyList = emptyList();
175
testCollection(emptyList);
176
testEmptyList(emptyList);
177
testEmptyList(EMPTY_LIST);
178
testEmptyList(Collections.emptyList());
179
testImmutableList(emptyList);
180
181
Map<Integer,Integer> emptyMap = emptyMap();
182
testMap(emptyMap);
183
testEmptyMap(emptyMap);
184
testEmptyMap(EMPTY_MAP);
185
testEmptyMap(Collections.emptyMap());
186
testEmptyMap(Collections.emptySortedMap());
187
testEmptyMap(Collections.emptyNavigableMap());
188
testImmutableMap(emptyMap);
189
testImmutableMap(Collections.emptyMap());
190
testImmutableMap(Collections.emptySortedMap());
191
testImmutableMap(Collections.emptyNavigableMap());
192
193
// Singleton collections
194
Set<Integer> singletonSet = singleton(1);
195
equal(singletonSet.size(), 1);
196
testCollection(singletonSet);
197
testImmutableSet(singletonSet);
198
199
List<Integer> singletonList = singletonList(1);
200
equal(singletonList.size(), 1);
201
testCollection(singletonList);
202
testImmutableList(singletonList);
203
testImmutableList(singletonList.subList(0,1));
204
testImmutableList(singletonList.subList(0,1).subList(0,1));
205
testEmptyList(singletonList.subList(0,0));
206
testEmptyList(singletonList.subList(0,0).subList(0,0));
207
208
Map<Integer,Integer> singletonMap = singletonMap(1,2);
209
equal(singletonMap.size(), 1);
210
testMap(singletonMap);
211
testImmutableMap(singletonMap);
212
213
// Immutable List
214
testEmptyList(List.of());
215
testEmptyList(List.of().subList(0,0));
216
testListMutatorsAlwaysThrow(List.of());
217
testListMutatorsAlwaysThrow(List.<Integer>of().subList(0,0));
218
testEmptyListMutatorsAlwaysThrow(List.of());
219
testEmptyListMutatorsAlwaysThrow(List.<Integer>of().subList(0,0));
220
for (List<Integer> list : Arrays.asList(
221
List.<Integer>of(),
222
List.of(1),
223
List.of(1, 2),
224
List.of(1, 2, 3),
225
List.of(1, 2, 3, 4),
226
List.of(1, 2, 3, 4, 5),
227
List.of(1, 2, 3, 4, 5, 6),
228
List.of(1, 2, 3, 4, 5, 6, 7),
229
List.of(1, 2, 3, 4, 5, 6, 7, 8),
230
List.of(1, 2, 3, 4, 5, 6, 7, 8, 9),
231
List.of(1, 2, 3, 4, 5, 6, 7, 8, 9, 10),
232
List.of(integerArray),
233
Stream.<Integer>empty().toList(),
234
Stream.of(1).toList(),
235
Stream.of(1, 2).toList(),
236
Stream.of(1, 2, 3).toList(),
237
Stream.of(1, 2, 3, 4).toList(),
238
Stream.of((Integer)null).toList(),
239
Stream.of(1, null).toList(),
240
Stream.of(1, null, 3).toList(),
241
Stream.of(1, null, 3, 4).toList())) {
242
testCollection(list);
243
testImmutableList(list);
244
testListMutatorsAlwaysThrow(list);
245
if (list.size() >= 1) {
246
// test subLists
247
List<Integer> headList = list.subList(0, list.size() - 1);
248
List<Integer> tailList = list.subList(1, list.size());
249
testCollection(headList);
250
testCollection(tailList);
251
testImmutableList(headList);
252
testImmutableList(tailList);
253
testListMutatorsAlwaysThrow(headList);
254
testListMutatorsAlwaysThrow(tailList);
255
}
256
}
257
258
List<Integer> listCopy = List.copyOf(Arrays.asList(1, 2, 3));
259
testCollection(listCopy);
260
testImmutableList(listCopy);
261
testListMutatorsAlwaysThrow(listCopy);
262
263
List<Integer> listCollected = Stream.of(1, 2, 3).collect(Collectors.toUnmodifiableList());
264
equal(listCollected, List.of(1, 2, 3));
265
testCollection(listCollected);
266
testImmutableList(listCollected);
267
testListMutatorsAlwaysThrow(listCollected);
268
269
// List indexOf / lastIndexOf
270
271
// 0 element
272
System.out.println("testListIndexOf size 0");
273
testListIndexOf(-1, -1);
274
275
System.out.println("testListIndexOf size 1");
276
testListIndexOf(-1, -1, 0);
277
testListIndexOf(0, 0, 1);
278
279
System.out.println("testListIndexOf size 2");
280
testListIndexOf(-1, -1, 0, 0);
281
testListIndexOf(0, 0, 1, 0);
282
testListIndexOf(0, 1, 1, 1);
283
testListIndexOf(1, 1, 0, 1);
284
285
286
System.out.println("testListIndexOf size 3");
287
testListIndexOf(-1, -1, 0, 0, 0);
288
testListIndexOf(0, 0, 1, 0, 0);
289
testListIndexOf(0, 1, 1, 1, 0);
290
testListIndexOf(1, 2, 0, 1, 1);
291
testListIndexOf(2, 2, 0, 0, 1);
292
293
System.out.println("testListIndexOf size N");
294
testListIndexOf(-1, -1, 0, 0, 0, 0, 0, 0, 0);
295
testListIndexOf(2, 6, 0, 0, 1, 0, 1, 0, 1);
296
testListIndexOf(4, 4, 0, 0, 0, 0, 1, 0, 0);
297
testListIndexOf(0, 6, 1, 1, 1, 1, 1, 1, 1);
298
testListIndexOf(0, 7, 1, 1, 1, 1, 1, 1, 1, 1);
299
testListIndexOf(0, 8, 1, 1, 1, 1, 1, 1, 1, 1, 1);
300
testListIndexOf(0, 9, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1);
301
testListIndexOf(0, 10, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1);
302
testListIndexOf(0, 11, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1);
303
testListIndexOf(0, 12, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1);
304
testListIndexOf(12, 12, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1);
305
testListIndexOf(-1, -1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0);
306
307
// Immutable Set
308
testEmptySet(Set.of());
309
testCollMutatorsAlwaysThrow(Set.of());
310
testEmptyCollMutatorsAlwaysThrow(Set.of());
311
for (Set<Integer> set : Arrays.asList(
312
Set.<Integer>of(),
313
Set.of(1),
314
Set.of(1, 2),
315
Set.of(1, 2, 3),
316
Set.of(1, 2, 3, 4),
317
Set.of(1, 2, 3, 4, 5),
318
Set.of(1, 2, 3, 4, 5, 6),
319
Set.of(1, 2, 3, 4, 5, 6, 7),
320
Set.of(1, 2, 3, 4, 5, 6, 7, 8),
321
Set.of(1, 2, 3, 4, 5, 6, 7, 8, 9),
322
Set.of(1, 2, 3, 4, 5, 6, 7, 8, 9, 10),
323
Set.of(integerArray))) {
324
testCollection(set);
325
testImmutableSet(set);
326
testCollMutatorsAlwaysThrow(set);
327
}
328
329
Set<Integer> setCopy = Set.copyOf(Arrays.asList(1, 2, 3));
330
testCollection(setCopy);
331
testImmutableSet(setCopy);
332
testCollMutatorsAlwaysThrow(setCopy);
333
334
Set<Integer> setCollected = Stream.of(1, 1, 2, 3, 2, 3)
335
.collect(Collectors.toUnmodifiableSet());
336
equal(setCollected, Set.of(1, 2, 3));
337
testCollection(setCollected);
338
testImmutableSet(setCollected);
339
testCollMutatorsAlwaysThrow(setCollected);
340
341
// Immutable Map
342
343
@SuppressWarnings("unchecked")
344
Map.Entry<Integer,Integer>[] ea = (Map.Entry<Integer,Integer>[])new Map.Entry<?,?>[20];
345
for (int i = 0; i < ea.length; i++) {
346
ea[i] = Map.entry(i+1, i+101);
347
}
348
349
testEmptyMap(Map.of());
350
testMapMutatorsAlwaysThrow(Map.of());
351
testEmptyMapMutatorsAlwaysThrow(Map.of());
352
for (Map<Integer,Integer> map : Arrays.asList(
353
Map.<Integer,Integer>of(),
354
Map.of(1, 101),
355
Map.of(1, 101, 2, 202),
356
Map.of(1, 101, 2, 202, 3, 303),
357
Map.of(1, 101, 2, 202, 3, 303, 4, 404),
358
Map.of(1, 101, 2, 202, 3, 303, 4, 404, 5, 505),
359
Map.of(1, 101, 2, 202, 3, 303, 4, 404, 5, 505, 6, 606),
360
Map.of(1, 101, 2, 202, 3, 303, 4, 404, 5, 505, 6, 606, 7, 707),
361
Map.of(1, 101, 2, 202, 3, 303, 4, 404, 5, 505, 6, 606, 7, 707, 8, 808),
362
Map.of(1, 101, 2, 202, 3, 303, 4, 404, 5, 505, 6, 606, 7, 707, 8, 808, 9, 909),
363
Map.of(1, 101, 2, 202, 3, 303, 4, 404, 5, 505, 6, 606, 7, 707, 8, 808, 9, 909, 10, 1010),
364
Map.ofEntries(ea))) {
365
testMap(map);
366
testImmutableMap(map);
367
testMapMutatorsAlwaysThrow(map);
368
}
369
370
Map<Integer,Integer> mapCopy = Map.copyOf(new HashMap<>(Map.of(1, 101, 2, 202, 3, 303)));
371
testMap(mapCopy);
372
testImmutableMap(mapCopy);
373
testMapMutatorsAlwaysThrow(mapCopy);
374
375
Map<Integer,Integer> mapCollected1 =
376
Stream.of(1, 2, 3)
377
.collect(Collectors.toUnmodifiableMap(i -> i, i -> 101 * i));
378
equal(mapCollected1, Map.of(1, 101, 2, 202, 3, 303));
379
testMap(mapCollected1);
380
testImmutableMap(mapCollected1);
381
testMapMutatorsAlwaysThrow(mapCollected1);
382
383
try {
384
Stream.of(1, 1, 2, 3, 2, 3)
385
.collect(Collectors.toUnmodifiableMap(i -> i, i -> 101 * i));
386
fail("duplicates should have thrown an exception");
387
} catch (IllegalStateException ise) {
388
pass();
389
}
390
391
Map<Integer,Integer> mapCollected2 =
392
Stream.of(1, 1, 2, 3, 2, 3)
393
.collect(Collectors.toUnmodifiableMap(i -> i, i -> 101 * i, Integer::sum));
394
equal(mapCollected2, Map.of(1, 202, 2, 404, 3, 606));
395
testMap(mapCollected2);
396
testImmutableMap(mapCollected2);
397
testMapMutatorsAlwaysThrow(mapCollected2);
398
}
399
400
private static void checkContainsSelf(Collection<Integer> c) {
401
check(c.containsAll(c));
402
check(c.containsAll(Arrays.asList(c.toArray())));
403
check(c.containsAll(Arrays.asList(c.toArray(new Integer[0]))));
404
}
405
406
private static void checkContainsEmpty(Collection<Integer> c) {
407
check(c.containsAll(new ArrayList<Integer>()));
408
}
409
410
private static void checkUnique(Set<Integer> s) {
411
for (Integer i : s) {
412
int count = 0;
413
for (Integer j : s) {
414
if (Objects.equals(i,j))
415
++count;
416
}
417
check(count == 1);
418
}
419
}
420
421
private static <T> void testEmptyCollection(Collection<T> c) {
422
check(c.isEmpty());
423
equal(c.size(), 0);
424
equal(c.toString(),"[]");
425
equal(c.toArray().length, 0);
426
equal(c.toArray(new Object[0]).length, 0);
427
equal(c.toArray(Object[]::new).length, 0);
428
check(c.toArray(new Object[]{42})[0] == null);
429
430
Object[] a = new Object[1]; a[0] = Boolean.TRUE;
431
equal(c.toArray(a), a);
432
equal(a[0], null);
433
testEmptyIterator(c.iterator());
434
}
435
436
static <T> void testEmptyIterator(final Iterator<T> it) {
437
if (rnd.nextBoolean())
438
check(! it.hasNext());
439
440
THROWS(NoSuchElementException.class, () -> it.next());
441
442
try { it.remove(); }
443
catch (IllegalStateException ignored) { pass(); }
444
catch (UnsupportedOperationException ignored) { pass(); }
445
catch (Throwable t) { unexpected(t); }
446
447
if (rnd.nextBoolean())
448
check(! it.hasNext());
449
}
450
451
private static void testEmptyList(List<?> c) {
452
testEmptyCollection(c);
453
equal(c.hashCode(), 1);
454
equal2(c, Collections.<Integer>emptyList());
455
}
456
457
private static <T> void testEmptySet(Set<T> c) {
458
testEmptyCollection(c);
459
equal(c.hashCode(), 0);
460
equal2(c, Collections.<Integer>emptySet());
461
if (c instanceof NavigableSet<?>)
462
testEmptyIterator(((NavigableSet<T>)c).descendingIterator());
463
}
464
465
private static void testImmutableCollection(final Collection<Integer> c) {
466
THROWS(UnsupportedOperationException.class,
467
() -> c.add(99),
468
() -> c.addAll(singleton(99)));
469
if (! c.isEmpty()) {
470
final Integer first = c.iterator().next();
471
THROWS(UnsupportedOperationException.class,
472
() -> c.clear(),
473
() -> c.remove(first),
474
() -> c.removeAll(singleton(first)),
475
() -> c.retainAll(emptyList()));
476
}
477
}
478
479
private static void testImmutableSet(final Set<Integer> c) {
480
testImmutableCollection(c);
481
}
482
483
private static void testImmutableList(final List<Integer> c) {
484
testList(c);
485
testImmutableCollection(c);
486
THROWS(UnsupportedOperationException.class,
487
() -> c.set(0,42),
488
() -> c.add(0,42),
489
() -> c.addAll(0,singleton(86)));
490
if (! c.isEmpty())
491
THROWS(UnsupportedOperationException.class,
492
() -> { Iterator<Integer> it = c.iterator();
493
it.next();
494
it.remove(); },
495
() -> { ListIterator<Integer> it = c.listIterator();
496
it.next();
497
it.remove(); });
498
}
499
500
/**
501
* Test that calling a mutator always throws UOE, even if the mutator
502
* wouldn't actually do anything, given its arguments.
503
*
504
* @param c the collection instance to test
505
*/
506
private static void testCollMutatorsAlwaysThrow(Collection<Integer> c) {
507
THROWS(UnsupportedOperationException.class,
508
() -> c.addAll(Collections.emptyList()),
509
() -> c.remove(ABSENT_VALUE),
510
() -> c.removeAll(Collections.emptyList()),
511
() -> c.removeIf(x -> false),
512
() -> c.retainAll(c));
513
}
514
515
/**
516
* Test that calling a mutator always throws UOE, even if the mutator
517
* wouldn't actually do anything on an empty collection.
518
*
519
* @param c the collection instance to test, must be empty
520
*/
521
private static void testEmptyCollMutatorsAlwaysThrow(Collection<Integer> c) {
522
if (! c.isEmpty()) {
523
fail("collection is not empty");
524
}
525
THROWS(UnsupportedOperationException.class,
526
() -> c.clear());
527
}
528
529
/**
530
* As above, for a list.
531
*
532
* @param c the list instance to test
533
*/
534
private static void testListMutatorsAlwaysThrow(List<Integer> c) {
535
testCollMutatorsAlwaysThrow(c);
536
THROWS(UnsupportedOperationException.class,
537
() -> c.addAll(0, Collections.emptyList()));
538
}
539
540
/**
541
* As above, for an empty list.
542
*
543
* @param c the list instance to test, must be empty
544
*/
545
private static void testEmptyListMutatorsAlwaysThrow(List<Integer> c) {
546
if (! c.isEmpty()) {
547
fail("list is not empty");
548
}
549
testEmptyCollMutatorsAlwaysThrow(c);
550
THROWS(UnsupportedOperationException.class,
551
() -> c.replaceAll(x -> x),
552
() -> c.sort(null));
553
}
554
555
/**
556
* As above, for a map.
557
*
558
* @param m the map instance to test
559
*/
560
private static void testMapMutatorsAlwaysThrow(Map<Integer,Integer> m) {
561
THROWS(UnsupportedOperationException.class,
562
() -> m.compute(ABSENT_VALUE, (k, v) -> null),
563
() -> m.computeIfAbsent(ABSENT_VALUE, k -> null),
564
() -> m.computeIfPresent(ABSENT_VALUE, (k, v) -> null),
565
() -> m.merge(ABSENT_VALUE, 0, (k, v) -> null),
566
() -> m.putAll(Collections.emptyMap()),
567
() -> m.remove(ABSENT_VALUE),
568
() -> m.remove(ABSENT_VALUE, 0),
569
() -> m.replace(ABSENT_VALUE, 0),
570
() -> m.replace(ABSENT_VALUE, 0, 1));
571
}
572
573
/**
574
* As above, for an empty map.
575
*
576
* @param map the map instance to test, must be empty
577
*/
578
private static void testEmptyMapMutatorsAlwaysThrow(Map<Integer,Integer> m) {
579
if (! m.isEmpty()) {
580
fail("map is not empty");
581
}
582
THROWS(UnsupportedOperationException.class,
583
() -> m.clear(),
584
() -> m.replaceAll((k, v) -> v));
585
}
586
587
private static void clear(Collection<Integer> c) {
588
try { c.clear(); }
589
catch (Throwable t) { unexpected(t); }
590
testEmptyCollection(c);
591
}
592
593
private static <K,V> void testEmptyMap(final Map<K,V> m) {
594
check(m.isEmpty());
595
equal(m.size(), 0);
596
equal(m.toString(),"{}");
597
testEmptySet(m.keySet());
598
testEmptySet(m.entrySet());
599
testEmptyCollection(m.values());
600
601
try { check(! m.containsValue(null)); }
602
catch (NullPointerException ignored) { /* OK */ }
603
try { check(! m.containsKey(null)); }
604
catch (NullPointerException ignored) { /* OK */ }
605
check(! m.containsValue(1));
606
check(! m.containsKey(1));
607
}
608
609
private static void testImmutableMap(final Map<Integer,Integer> m) {
610
THROWS(UnsupportedOperationException.class,
611
() -> m.put(1,1),
612
() -> m.putAll(singletonMap(1,1)));
613
if (! m.isEmpty()) {
614
final Integer first = m.keySet().iterator().next();
615
THROWS(UnsupportedOperationException.class,
616
() -> m.remove(first),
617
() -> m.clear());
618
final Map.Entry<Integer,Integer> me
619
= m.entrySet().iterator().next();
620
Integer key = me.getKey();
621
Integer val = me.getValue();
622
THROWS(UnsupportedOperationException.class,
623
() -> me.setValue(3));
624
equal(key, me.getKey());
625
equal(val, me.getValue());
626
}
627
testImmutableSet(m.keySet());
628
testImmutableCollection(m.values());
629
//testImmutableSet(m.entrySet());
630
}
631
632
private static void clear(Map<?,?> m) {
633
try { m.clear(); }
634
catch (Throwable t) { unexpected(t); }
635
testEmptyMap(m);
636
}
637
638
private static void oneElement(Collection<Integer> c) {
639
clear(c);
640
try {
641
check(c.add(-42));
642
equal(c.toString(), "[-42]");
643
if (c instanceof Set) check(! c.add(-42));
644
} catch (Throwable t) { unexpected(t); }
645
check(! c.isEmpty()); check(c.size() == 1);
646
}
647
648
private static boolean supportsAdd(Collection<Integer> c) {
649
try { check(c.add(ABSENT_VALUE)); }
650
catch (UnsupportedOperationException t) { return false; }
651
catch (Throwable t) { unexpected(t); }
652
653
try {
654
check(c.contains(ABSENT_VALUE));
655
check(c.remove(ABSENT_VALUE));
656
} catch (Throwable t) { unexpected(t); }
657
return true;
658
}
659
660
private static boolean supportsRemove(Collection<Integer> c) {
661
try { check(! c.remove(ABSENT_VALUE)); }
662
catch (UnsupportedOperationException t) { return false; }
663
catch (Throwable t) { unexpected(t); }
664
return true;
665
}
666
667
// 6260652: (coll) Arrays.asList(x).toArray().getClass()
668
// should be Object[].class
669
// Fixed in jdk9, but not jdk8 ...
670
static final boolean needToWorkAround6260652 =
671
Arrays.asList("").toArray().getClass() != Object[].class;
672
673
private static void checkFunctionalInvariants(Collection<Integer> c) {
674
try {
675
checkContainsSelf(c);
676
checkContainsEmpty(c);
677
check(c.size() != 0 ^ c.isEmpty());
678
check(! c.contains(ABSENT_VALUE));
679
680
{
681
int size = 0;
682
for (Integer i : c) size++;
683
check(c.size() == size);
684
}
685
686
if (c instanceof Set) {
687
checkUnique((Set<Integer>)c);
688
}
689
690
check(c.toArray().length == c.size());
691
check(c.toArray().getClass() == Object[].class
692
||
693
(needToWorkAround6260652 &&
694
c.getClass().getName().equals("java.util.Arrays$ArrayList")));
695
for (int size : new int[]{0,1,c.size(), c.size()+1}) {
696
Integer[] a = c.toArray(new Integer[size]);
697
check((size > c.size()) || a.length == c.size());
698
int i = 0; for (Integer j : c) check(a[i++] == j);
699
check((size <= c.size()) || (a[c.size()] == null));
700
check(a.getClass() == Integer[].class);
701
}
702
703
{
704
Integer[] a = c.toArray(Integer[]::new);
705
equal(c.size(), a.length);
706
check(a.getClass() == Integer[].class);
707
check(Arrays.equals(c.toArray(new Integer[0]), a));
708
}
709
710
check(c.equals(c));
711
if (c instanceof Serializable) {
712
//System.out.printf("Serializing %s%n", c.getClass().getName());
713
try {
714
Object clone = serialClone(c);
715
equal(c instanceof Serializable,
716
clone instanceof Serializable);
717
equal(c instanceof RandomAccess,
718
clone instanceof RandomAccess);
719
if ((c instanceof List) || (c instanceof Set))
720
equal(c, clone);
721
else
722
equal(new HashSet<Integer>(c),
723
new HashSet<Integer>(serialClone(c)));
724
} catch (Error xxx) {
725
if (! (xxx.getCause() instanceof NotSerializableException))
726
throw xxx;
727
}
728
}
729
}
730
catch (Throwable t) { unexpected(t); }
731
}
732
733
//----------------------------------------------------------------
734
// If add(null) succeeds, contains(null) & remove(null) should succeed
735
//----------------------------------------------------------------
736
private static void testNullElement(Collection<Integer> c) {
737
738
try {
739
check(c.add(null));
740
if (c.size() == 1)
741
equal(c.toString(), "[null]");
742
try {
743
checkFunctionalInvariants(c);
744
check(c.contains(null));
745
check(c.remove(null));
746
}
747
catch (Throwable t) { unexpected(t); }
748
}
749
catch (NullPointerException e) { /* OK */ }
750
catch (Throwable t) { unexpected(t); }
751
}
752
753
//----------------------------------------------------------------
754
// If add("x") succeeds, contains("x") & remove("x") should succeed
755
//----------------------------------------------------------------
756
@SuppressWarnings("unchecked")
757
private static void testStringElement(Collection<Integer> c) {
758
Collection x = (Collection)c; // Make type-unsafe
759
try {
760
check(x.add("x"));
761
try {
762
check(x.contains("x"));
763
check(x.remove("x"));
764
} catch (Throwable t) { unexpected(t); }
765
}
766
catch (ClassCastException e) { /* OK */ }
767
catch (Throwable t) { unexpected(t); }
768
}
769
770
private static void testConcurrentCollection(Collection<Integer> c) {
771
try {
772
c.add(1);
773
Iterator<Integer> it = c.iterator();
774
check(it.hasNext());
775
clear(c);
776
check(it.next() instanceof Integer); // No CME
777
check(c.isEmpty());
778
}
779
catch (Throwable t) { unexpected(t); }
780
}
781
782
private static void testQueue(Queue<Integer> q) {
783
q.clear();
784
for (int i = 0; i < 5; i++) {
785
testQueueAddRemove(q, null);
786
testQueueAddRemove(q, 537);
787
q.add(i);
788
}
789
equal(q.size(), 5);
790
checkFunctionalInvariants(q);
791
q.poll();
792
equal(q.size(), 4);
793
checkFunctionalInvariants(q);
794
if ((q instanceof LinkedBlockingQueue) ||
795
(q instanceof LinkedBlockingDeque) ||
796
(q instanceof ConcurrentLinkedDeque) ||
797
(q instanceof ConcurrentLinkedQueue)) {
798
testQueueIteratorRemove(q);
799
}
800
}
801
802
private static void testQueueAddRemove(final Queue<Integer> q,
803
final Integer e) {
804
final List<Integer> originalContents = new ArrayList<>(q);
805
final boolean isEmpty = q.isEmpty();
806
final boolean isList = (q instanceof List);
807
final List asList = isList ? (List) q : null;
808
check(!q.contains(e));
809
try {
810
q.add(e);
811
} catch (NullPointerException npe) {
812
check(e == null);
813
return; // Null elements not supported
814
}
815
check(q.contains(e));
816
check(q.remove(e));
817
check(!q.contains(e));
818
equal(new ArrayList<Integer>(q), originalContents);
819
820
if (q instanceof Deque<?>) {
821
final Deque<Integer> deq = (Deque<Integer>) q;
822
final List<Integer> singleton = Collections.singletonList(e);
823
824
// insert, query, remove element at head
825
if (isEmpty) {
826
THROWS(NoSuchElementException.class,
827
() -> deq.getFirst(),
828
() -> deq.element(),
829
() -> deq.iterator().next());
830
check(deq.peekFirst() == null);
831
check(deq.peek() == null);
832
} else {
833
check(deq.getFirst() != e);
834
check(deq.element() != e);
835
check(deq.iterator().next() != e);
836
check(deq.peekFirst() != e);
837
check(deq.peek() != e);
838
}
839
check(!deq.contains(e));
840
check(!deq.removeFirstOccurrence(e));
841
check(!deq.removeLastOccurrence(e));
842
if (isList) {
843
check(asList.indexOf(e) == -1);
844
check(asList.lastIndexOf(e) == -1);
845
}
846
switch (rnd.nextInt(isList ? 4 : 3)) {
847
case 0: deq.addFirst(e); break;
848
case 1: check(deq.offerFirst(e)); break;
849
case 2: deq.push(e); break;
850
case 3: asList.add(0, e); break;
851
default: throw new AssertionError();
852
}
853
check(deq.peekFirst() == e);
854
check(deq.getFirst() == e);
855
check(deq.element() == e);
856
check(deq.peek() == e);
857
check(deq.iterator().next() == e);
858
check(deq.contains(e));
859
if (isList) {
860
check(asList.get(0) == e);
861
check(asList.indexOf(e) == 0);
862
check(asList.lastIndexOf(e) == 0);
863
check(asList.subList(0, 1).equals(singleton));
864
}
865
switch (rnd.nextInt(isList ? 11 : 9)) {
866
case 0: check(deq.pollFirst() == e); break;
867
case 1: check(deq.removeFirst() == e); break;
868
case 2: check(deq.remove() == e); break;
869
case 3: check(deq.pop() == e); break;
870
case 4: check(deq.removeFirstOccurrence(e)); break;
871
case 5: check(deq.removeLastOccurrence(e)); break;
872
case 6: check(deq.remove(e)); break;
873
case 7: check(deq.removeAll(singleton)); break;
874
case 8: Iterator it = deq.iterator(); it.next(); it.remove(); break;
875
case 9: asList.remove(0); break;
876
case 10: asList.subList(0, 1).clear(); break;
877
default: throw new AssertionError();
878
}
879
if (isEmpty) {
880
THROWS(NoSuchElementException.class,
881
() -> deq.getFirst(),
882
() -> deq.element(),
883
() -> deq.iterator().next());
884
check(deq.peekFirst() == null);
885
check(deq.peek() == null);
886
} else {
887
check(deq.getFirst() != e);
888
check(deq.element() != e);
889
check(deq.iterator().next() != e);
890
check(deq.peekFirst() != e);
891
check(deq.peek() != e);
892
}
893
check(!deq.contains(e));
894
check(!deq.removeFirstOccurrence(e));
895
check(!deq.removeLastOccurrence(e));
896
if (isList) {
897
check(isEmpty || asList.get(0) != e);
898
check(asList.indexOf(e) == -1);
899
check(asList.lastIndexOf(e) == -1);
900
}
901
equal(new ArrayList<Integer>(deq), originalContents);
902
903
// insert, query, remove element at tail
904
if (isEmpty) {
905
check(deq.peekLast() == null);
906
THROWS(NoSuchElementException.class, () -> deq.getLast());
907
} else {
908
check(deq.peekLast() != e);
909
check(deq.getLast() != e);
910
}
911
switch (rnd.nextInt(isList ? 6 : 4)) {
912
case 0: deq.addLast(e); break;
913
case 1: check(deq.offerLast(e)); break;
914
case 2: check(deq.add(e)); break;
915
case 3: deq.addAll(singleton); break;
916
case 4: asList.addAll(deq.size(), singleton); break;
917
case 5: asList.add(deq.size(), e); break;
918
default: throw new AssertionError();
919
}
920
check(deq.peekLast() == e);
921
check(deq.getLast() == e);
922
check(deq.contains(e));
923
if (isList) {
924
ListIterator it = asList.listIterator(asList.size());
925
check(it.previous() == e);
926
check(asList.get(asList.size() - 1) == e);
927
check(asList.indexOf(e) == asList.size() - 1);
928
check(asList.lastIndexOf(e) == asList.size() - 1);
929
int size = asList.size();
930
check(asList.subList(size - 1, size).equals(singleton));
931
}
932
switch (rnd.nextInt(isList ? 8 : 6)) {
933
case 0: check(deq.pollLast() == e); break;
934
case 1: check(deq.removeLast() == e); break;
935
case 2: check(deq.removeFirstOccurrence(e)); break;
936
case 3: check(deq.removeLastOccurrence(e)); break;
937
case 4: check(deq.remove(e)); break;
938
case 5: check(deq.removeAll(singleton)); break;
939
case 6: asList.remove(asList.size() - 1); break;
940
case 7:
941
ListIterator it = asList.listIterator(asList.size());
942
it.previous();
943
it.remove();
944
break;
945
default: throw new AssertionError();
946
}
947
if (isEmpty) {
948
check(deq.peekLast() == null);
949
THROWS(NoSuchElementException.class, () -> deq.getLast());
950
} else {
951
check(deq.peekLast() != e);
952
check(deq.getLast() != e);
953
}
954
check(!deq.contains(e));
955
equal(new ArrayList<Integer>(deq), originalContents);
956
957
// Test operations on empty deque
958
switch (rnd.nextInt(isList ? 4 : 2)) {
959
case 0: deq.clear(); break;
960
case 1:
961
Iterator it = deq.iterator();
962
while (it.hasNext()) {
963
it.next();
964
it.remove();
965
}
966
break;
967
case 2: asList.subList(0, asList.size()).clear(); break;
968
case 3:
969
ListIterator lit = asList.listIterator(asList.size());
970
while (lit.hasPrevious()) {
971
lit.previous();
972
lit.remove();
973
}
974
break;
975
default: throw new AssertionError();
976
}
977
testEmptyCollection(deq);
978
check(!deq.iterator().hasNext());
979
if (isList) {
980
check(!asList.listIterator().hasPrevious());
981
THROWS(NoSuchElementException.class,
982
() -> asList.listIterator().previous());
983
}
984
THROWS(NoSuchElementException.class,
985
() -> deq.iterator().next(),
986
() -> deq.element(),
987
() -> deq.getFirst(),
988
() -> deq.getLast(),
989
() -> deq.pop(),
990
() -> deq.remove(),
991
() -> deq.removeFirst(),
992
() -> deq.removeLast());
993
994
check(deq.poll() == null);
995
check(deq.pollFirst() == null);
996
check(deq.pollLast() == null);
997
check(deq.peek() == null);
998
check(deq.peekFirst() == null);
999
check(deq.peekLast() == null);
1000
check(!deq.removeFirstOccurrence(e));
1001
check(!deq.removeLastOccurrence(e));
1002
1003
check(deq.addAll(originalContents) == !isEmpty);
1004
equal(new ArrayList<Integer>(deq), originalContents);
1005
check(!deq.addAll(Collections.<Integer>emptyList()));
1006
equal(new ArrayList<Integer>(deq), originalContents);
1007
}
1008
}
1009
1010
private static void testQueueIteratorRemove(Queue<Integer> q) {
1011
System.err.printf("testQueueIteratorRemove %s%n",
1012
q.getClass().getSimpleName());
1013
q.clear();
1014
for (int i = 0; i < 5; i++)
1015
q.add(i);
1016
Iterator<Integer> it = q.iterator();
1017
check(it.hasNext());
1018
for (int i = 3; i >= 0; i--)
1019
q.remove(i);
1020
equal(it.next(), 0);
1021
equal(it.next(), 4);
1022
1023
q.clear();
1024
for (int i = 0; i < 5; i++)
1025
q.add(i);
1026
it = q.iterator();
1027
equal(it.next(), 0);
1028
check(it.hasNext());
1029
for (int i = 1; i < 4; i++)
1030
q.remove(i);
1031
equal(it.next(), 1);
1032
equal(it.next(), 4);
1033
}
1034
1035
// for any array of integer values, check that the result of lastIndexOf(1)
1036
// and indexOf(1) match assumptions for all types of List<Integer> we can
1037
// construct
1038
private static void testListIndexOf(final int index,
1039
final int lastIndex,
1040
final Integer ... values) {
1041
if (values.length == 0) {
1042
checkListIndexOf(emptyList(), index, lastIndex);
1043
} else if (values.length == 1) {
1044
checkListIndexOf(singletonList(values[0]), index, lastIndex);
1045
checkListIndexOf(nCopies(25, values[0]), index, lastIndex == 0 ? 24 : -1);
1046
}
1047
List<Integer> l = List.of(values);
1048
checkListIndexOf(l, index, lastIndex);
1049
checkListIndexOf(Arrays.asList(values), index, lastIndex);
1050
checkListIndexOf(new ArrayList(l), index, lastIndex);
1051
checkListIndexOf(new LinkedList(l), index, lastIndex);
1052
checkListIndexOf(new Vector(l), index, lastIndex);
1053
checkListIndexOf(new CopyOnWriteArrayList(l), index, lastIndex);
1054
}
1055
1056
private static void checkListIndexOf(final List<Integer> list,
1057
final int index,
1058
final int lastIndex) {
1059
String msg = list.getClass().toString();
1060
equal(list.indexOf(1), index, msg);
1061
equal(list.lastIndexOf(1), lastIndex, msg);
1062
equal(list.subList(0, list.size()).indexOf(1), index, msg);
1063
equal(list.subList(0, list.size()).lastIndexOf(1), lastIndex, msg);
1064
}
1065
1066
private static void testList(final List<Integer> l) {
1067
//----------------------------------------------------------------
1068
// 4802633: (coll) AbstractList.addAll(-1,emptyCollection)
1069
// doesn't throw IndexOutOfBoundsException
1070
//----------------------------------------------------------------
1071
try {
1072
l.addAll(-1, Collections.<Integer>emptyList());
1073
fail("Expected IndexOutOfBoundsException not thrown");
1074
}
1075
catch (UnsupportedOperationException ignored) {/* OK */}
1076
catch (IndexOutOfBoundsException ignored) {/* OK */}
1077
catch (Throwable t) { unexpected(t); }
1078
1079
// equal(l instanceof Serializable,
1080
// l.subList(0,0) instanceof Serializable);
1081
if (l.subList(0,0) instanceof Serializable)
1082
check(l instanceof Serializable);
1083
1084
equal(l instanceof RandomAccess,
1085
l.subList(0,0) instanceof RandomAccess);
1086
1087
l.iterator();
1088
l.listIterator();
1089
l.listIterator(0);
1090
l.listIterator(l.size());
1091
THROWS(IndexOutOfBoundsException.class,
1092
() -> l.listIterator(-1),
1093
() -> l.listIterator(l.size() + 1));
1094
1095
if (l instanceof AbstractList) {
1096
try {
1097
int size = l.size();
1098
AbstractList<Integer> abList = (AbstractList<Integer>) l;
1099
Method m = AbstractList.class.getDeclaredMethod("removeRange", new Class[] { int.class, int.class });
1100
m.setAccessible(true);
1101
m.invoke(abList, new Object[] { 0, 0 });
1102
m.invoke(abList, new Object[] { size, size });
1103
equal(size, l.size());
1104
}
1105
catch (UnsupportedOperationException ignored) {/* OK */}
1106
catch (Throwable t) { unexpected(t); }
1107
}
1108
1109
int hashCode = 1;
1110
for (Integer i : l)
1111
hashCode = 31 * hashCode + (i == null ? 0 : i.hashCode());
1112
check(l.hashCode() == hashCode);
1113
1114
var t = new ArrayList<>(l);
1115
check(t.equals(l));
1116
check(l.equals(t));
1117
}
1118
1119
private static void testCollection(Collection<Integer> c) {
1120
try { testCollection1(c); }
1121
catch (Throwable t) { unexpected(t); }
1122
}
1123
1124
private static void testCollection1(Collection<Integer> c) {
1125
1126
System.out.println("\n==> " + c.getClass().getName());
1127
1128
checkFunctionalInvariants(c);
1129
1130
if (! supportsAdd(c)) return;
1131
//System.out.println("add() supported");
1132
1133
if (c instanceof NavigableSet) {
1134
System.out.println("NavigableSet tests...");
1135
1136
NavigableSet<Integer> ns = (NavigableSet<Integer>)c;
1137
testNavigableSet(ns);
1138
testNavigableSet(ns.headSet(6, false));
1139
testNavigableSet(ns.headSet(5, true));
1140
testNavigableSet(ns.tailSet(0, false));
1141
testNavigableSet(ns.tailSet(1, true));
1142
testNavigableSet(ns.subSet(0, false, 5, true));
1143
testNavigableSet(ns.subSet(1, true, 6, false));
1144
}
1145
1146
if (c instanceof Queue)
1147
testQueue((Queue<Integer>)c);
1148
1149
if (c instanceof List)
1150
testList((List<Integer>)c);
1151
1152
if (c instanceof Set) {
1153
int hashCode = 0;
1154
for (Integer i : c)
1155
hashCode = hashCode + (i == null ? 0 : i.hashCode());
1156
check(c.hashCode() == hashCode);
1157
}
1158
1159
check(supportsRemove(c));
1160
1161
try {
1162
oneElement(c);
1163
checkFunctionalInvariants(c);
1164
}
1165
catch (Throwable t) { unexpected(t); }
1166
1167
clear(c); testNullElement(c);
1168
oneElement(c); testNullElement(c);
1169
1170
clear(c); testStringElement(c);
1171
oneElement(c); testStringElement(c);
1172
1173
if (c.getClass().getName().matches(".*concurrent.*"))
1174
testConcurrentCollection(c);
1175
1176
//----------------------------------------------------------------
1177
// The "all" operations should throw NPE when passed null
1178
//----------------------------------------------------------------
1179
{
1180
clear(c);
1181
try {
1182
c.removeAll(null);
1183
fail("Expected NullPointerException");
1184
}
1185
catch (NullPointerException e) { pass(); }
1186
catch (Throwable t) { unexpected(t); }
1187
1188
oneElement(c);
1189
try {
1190
c.removeAll(null);
1191
fail("Expected NullPointerException");
1192
}
1193
catch (NullPointerException e) { pass(); }
1194
catch (Throwable t) { unexpected(t); }
1195
1196
clear(c);
1197
try {
1198
c.retainAll(null);
1199
fail("Expected NullPointerException");
1200
}
1201
catch (NullPointerException e) { pass(); }
1202
catch (Throwable t) { unexpected(t); }
1203
1204
oneElement(c);
1205
try {
1206
c.retainAll(null);
1207
fail("Expected NullPointerException");
1208
}
1209
catch (NullPointerException e) { pass(); }
1210
catch (Throwable t) { unexpected(t); }
1211
1212
oneElement(c);
1213
try {
1214
c.addAll(null);
1215
fail("Expected NullPointerException");
1216
}
1217
catch (NullPointerException e) { pass(); }
1218
catch (Throwable t) { unexpected(t); }
1219
1220
oneElement(c);
1221
try {
1222
c.containsAll(null);
1223
fail("Expected NullPointerException");
1224
}
1225
catch (NullPointerException e) { pass(); }
1226
catch (Throwable t) { unexpected(t); }
1227
}
1228
}
1229
1230
//----------------------------------------------------------------
1231
// Map
1232
//----------------------------------------------------------------
1233
private static void checkFunctionalInvariants(Map<Integer,Integer> m) {
1234
check(m.keySet().size() == m.entrySet().size());
1235
check(m.keySet().size() == m.size());
1236
checkFunctionalInvariants(m.keySet());
1237
checkFunctionalInvariants(m.values());
1238
check(m.size() != 0 ^ m.isEmpty());
1239
check(! m.containsKey(ABSENT_VALUE));
1240
1241
if (m instanceof Serializable) {
1242
//System.out.printf("Serializing %s%n", m.getClass().getName());
1243
try {
1244
Object clone = serialClone(m);
1245
equal(m instanceof Serializable,
1246
clone instanceof Serializable);
1247
equal(m, clone);
1248
} catch (Error xxx) {
1249
if (! (xxx.getCause() instanceof NotSerializableException))
1250
throw xxx;
1251
}
1252
}
1253
}
1254
1255
private static void testMap(Map<Integer,Integer> m) {
1256
System.out.println("\n==> " + m.getClass().getName());
1257
1258
int hashCode = 0;
1259
for (var e : m.entrySet()) {
1260
int entryHash = (e.getKey() == null ? 0 : e.getKey().hashCode()) ^
1261
(e.getValue() == null ? 0 : e.getValue().hashCode());
1262
check(e.hashCode() == entryHash);
1263
hashCode += entryHash;
1264
}
1265
check(m.hashCode() == hashCode);
1266
1267
if (m instanceof ConcurrentMap)
1268
testConcurrentMap((ConcurrentMap<Integer,Integer>) m);
1269
1270
if (m instanceof NavigableMap) {
1271
System.out.println("NavigableMap tests...");
1272
1273
NavigableMap<Integer,Integer> nm =
1274
(NavigableMap<Integer,Integer>) m;
1275
testNavigableMapRemovers(nm);
1276
testNavigableMap(nm);
1277
testNavigableMap(nm.headMap(6, false));
1278
testNavigableMap(nm.headMap(5, true));
1279
testNavigableMap(nm.tailMap(0, false));
1280
testNavigableMap(nm.tailMap(1, true));
1281
testNavigableMap(nm.subMap(1, true, 6, false));
1282
testNavigableMap(nm.subMap(0, false, 5, true));
1283
}
1284
1285
checkFunctionalInvariants(m);
1286
1287
if (supportsClear(m)) {
1288
try { clear(m); }
1289
catch (Throwable t) { unexpected(t); }
1290
}
1291
1292
if (supportsPut(m)) {
1293
try {
1294
check(m.put(3333, 77777) == null);
1295
check(m.put(9134, 74982) == null);
1296
check(m.get(9134) == 74982);
1297
check(m.put(9134, 1382) == 74982);
1298
check(m.get(9134) == 1382);
1299
check(m.size() == 2);
1300
checkFunctionalInvariants(m);
1301
checkNPEConsistency(m);
1302
}
1303
catch (Throwable t) { unexpected(t); }
1304
}
1305
}
1306
1307
private static boolean supportsPut(Map<Integer,Integer> m) {
1308
// We're asking for .equals(...) semantics
1309
if (m instanceof IdentityHashMap) return false;
1310
1311
try { check(m.put(ABSENT_VALUE,12735) == null); }
1312
catch (UnsupportedOperationException t) { return false; }
1313
catch (Throwable t) { unexpected(t); }
1314
1315
try {
1316
check(m.containsKey(ABSENT_VALUE));
1317
check(m.remove(ABSENT_VALUE) != null);
1318
} catch (Throwable t) { unexpected(t); }
1319
return true;
1320
}
1321
1322
private static boolean supportsClear(Map<?,?> m) {
1323
try { m.clear(); }
1324
catch (UnsupportedOperationException t) { return false; }
1325
catch (Throwable t) { unexpected(t); }
1326
return true;
1327
}
1328
1329
//----------------------------------------------------------------
1330
// ConcurrentMap
1331
//----------------------------------------------------------------
1332
private static void testConcurrentMap(ConcurrentMap<Integer,Integer> m) {
1333
System.out.println("ConcurrentMap tests...");
1334
1335
try {
1336
clear(m);
1337
1338
check(m.putIfAbsent(18357,7346) == null);
1339
check(m.containsKey(18357));
1340
check(m.putIfAbsent(18357,8263) == 7346);
1341
try { m.putIfAbsent(18357,null); fail("NPE"); }
1342
catch (NullPointerException t) { }
1343
check(m.containsKey(18357));
1344
1345
check(! m.replace(18357,8888,7777));
1346
check(m.containsKey(18357));
1347
try { m.replace(18357,null,7777); fail("NPE"); }
1348
catch (NullPointerException t) { }
1349
check(m.containsKey(18357));
1350
check(m.get(18357) == 7346);
1351
check(m.replace(18357,7346,5555));
1352
check(m.replace(18357,5555,7346));
1353
check(m.get(18357) == 7346);
1354
1355
check(m.replace(92347,7834) == null);
1356
try { m.replace(18357,null); fail("NPE"); }
1357
catch (NullPointerException t) { }
1358
check(m.replace(18357,7346) == 7346);
1359
check(m.replace(18357,5555) == 7346);
1360
check(m.get(18357) == 5555);
1361
check(m.replace(18357,7346) == 5555);
1362
check(m.get(18357) == 7346);
1363
1364
check(! m.remove(18357,9999));
1365
check(m.get(18357) == 7346);
1366
check(m.containsKey(18357));
1367
check(! m.remove(18357,null)); // 6272521
1368
check(m.get(18357) == 7346);
1369
check(m.remove(18357,7346));
1370
check(m.get(18357) == null);
1371
check(! m.containsKey(18357));
1372
check(m.isEmpty());
1373
1374
m.putIfAbsent(1,2);
1375
check(m.size() == 1);
1376
check(! m.remove(1,null));
1377
check(! m.remove(1,null));
1378
check(! m.remove(1,1));
1379
check(m.remove(1,2));
1380
check(m.isEmpty());
1381
1382
testEmptyMap(m);
1383
}
1384
catch (Throwable t) { unexpected(t); }
1385
}
1386
1387
private static void throwsConsistently(Class<? extends Throwable> k,
1388
Iterable<Fun> fs) {
1389
List<Class<? extends Throwable>> threw = new ArrayList<>();
1390
for (Fun f : fs)
1391
try { f.f(); threw.add(null); }
1392
catch (Throwable t) {
1393
check(k.isAssignableFrom(t.getClass()));
1394
threw.add(t.getClass());
1395
}
1396
if (new HashSet<Object>(threw).size() != 1)
1397
fail(threw.toString());
1398
}
1399
1400
private static <T> void checkNPEConsistency(final Map<T,Integer> m) {
1401
m.clear();
1402
final ConcurrentMap<T,Integer> cm = (m instanceof ConcurrentMap)
1403
? (ConcurrentMap<T,Integer>) m
1404
: null;
1405
List<Fun> fs = new ArrayList<>();
1406
fs.add(() -> check(! m.containsKey(null)));
1407
fs.add(() -> equal(m.remove(null), null));
1408
fs.add(() -> equal(m.get(null), null));
1409
if (cm != null)
1410
fs.add(() -> check(! cm.remove(null,null)));
1411
throwsConsistently(NullPointerException.class, fs);
1412
1413
fs.clear();
1414
final Map<T,Integer> sm = singletonMap(null,1);
1415
fs.add(() -> { equal(m.put(null,1), null); m.clear();});
1416
fs.add(() -> { m.putAll(sm); m.clear();});
1417
if (cm != null) {
1418
fs.add(() -> check(! cm.remove(null,null)));
1419
fs.add(() -> equal(cm.putIfAbsent(null,1), 1));
1420
fs.add(() -> equal(cm.replace(null,1), null));
1421
fs.add(() -> equal(cm.replace(null,1, 1), 1));
1422
}
1423
throwsConsistently(NullPointerException.class, fs);
1424
}
1425
1426
//----------------------------------------------------------------
1427
// NavigableMap
1428
//----------------------------------------------------------------
1429
private static void
1430
checkNavigableMapKeys(NavigableMap<Integer,Integer> m,
1431
Integer i,
1432
Integer lower,
1433
Integer floor,
1434
Integer ceiling,
1435
Integer higher) {
1436
equal(m.lowerKey(i), lower);
1437
equal(m.floorKey(i), floor);
1438
equal(m.ceilingKey(i), ceiling);
1439
equal(m.higherKey(i), higher);
1440
}
1441
1442
private static void
1443
checkNavigableSetKeys(NavigableSet<Integer> m,
1444
Integer i,
1445
Integer lower,
1446
Integer floor,
1447
Integer ceiling,
1448
Integer higher) {
1449
equal(m.lower(i), lower);
1450
equal(m.floor(i), floor);
1451
equal(m.ceiling(i), ceiling);
1452
equal(m.higher(i), higher);
1453
}
1454
1455
static final Random rnd = new Random();
1456
static void equalNext(final Iterator<?> it, Object expected) {
1457
if (rnd.nextBoolean())
1458
check(it.hasNext());
1459
equal(it.next(), expected);
1460
}
1461
1462
static void equalMaps(Map m1, Map m2) {
1463
equal(m1, m2);
1464
equal(m2, m1);
1465
equal(m1.size(), m2.size());
1466
equal(m1.isEmpty(), m2.isEmpty());
1467
equal(m1.toString(), m2.toString());
1468
check(Arrays.equals(m1.entrySet().toArray(), m2.entrySet().toArray()));
1469
}
1470
1471
@SuppressWarnings({"unchecked", "rawtypes"})
1472
static void testNavigableMapRemovers(NavigableMap m)
1473
{
1474
final Map emptyMap = new HashMap();
1475
1476
final Map singletonMap = new HashMap();
1477
singletonMap.put(1, 2);
1478
1479
abstract class NavigableMapView {
1480
abstract NavigableMap view(NavigableMap m);
1481
}
1482
1483
NavigableMapView[] views = {
1484
new NavigableMapView() { NavigableMap view(NavigableMap m) {
1485
return m; }},
1486
new NavigableMapView() { NavigableMap view(NavigableMap m) {
1487
return m.headMap(99, true); }},
1488
new NavigableMapView() { NavigableMap view(NavigableMap m) {
1489
return m.tailMap(-99, false); }},
1490
new NavigableMapView() { NavigableMap view(NavigableMap m) {
1491
return m.subMap(-99, true, 99, false); }},
1492
};
1493
1494
abstract class Remover {
1495
abstract void remove(NavigableMap m, Object k, Object v);
1496
}
1497
1498
Remover[] removers = {
1499
new Remover() { void remove(NavigableMap m, Object k, Object v) {
1500
equal(m.remove(k), v); }},
1501
1502
new Remover() { void remove(NavigableMap m, Object k, Object v) {
1503
equal(m.descendingMap().remove(k), v); }},
1504
new Remover() { void remove(NavigableMap m, Object k, Object v) {
1505
equal(m.descendingMap().headMap(-86, false).remove(k), v); }},
1506
new Remover() { void remove(NavigableMap m, Object k, Object v) {
1507
equal(m.descendingMap().tailMap(86, true).remove(k), v); }},
1508
1509
new Remover() { void remove(NavigableMap m, Object k, Object v) {
1510
equal(m.headMap(86, true).remove(k), v); }},
1511
new Remover() { void remove(NavigableMap m, Object k, Object v) {
1512
equal(m.tailMap(-86, true).remove(k), v); }},
1513
new Remover() { void remove(NavigableMap m, Object k, Object v) {
1514
equal(m.subMap(-86, false, 86, true).remove(k), v); }},
1515
1516
new Remover() { void remove(NavigableMap m, Object k, Object v) {
1517
check(m.keySet().remove(k)); }},
1518
new Remover() { void remove(NavigableMap m, Object k, Object v) {
1519
check(m.navigableKeySet().remove(k)); }},
1520
1521
new Remover() { void remove(NavigableMap m, Object k, Object v) {
1522
check(m.navigableKeySet().headSet(86, true).remove(k)); }},
1523
new Remover() { void remove(NavigableMap m, Object k, Object v) {
1524
check(m.navigableKeySet().tailSet(-86, false).remove(k)); }},
1525
new Remover() { void remove(NavigableMap m, Object k, Object v) {
1526
check(m.navigableKeySet().subSet(-86, true, 86, false)
1527
.remove(k)); }},
1528
1529
new Remover() { void remove(NavigableMap m, Object k, Object v) {
1530
check(m.descendingKeySet().headSet(-86, false).remove(k)); }},
1531
new Remover() { void remove(NavigableMap m, Object k, Object v) {
1532
check(m.descendingKeySet().tailSet(86, true).remove(k)); }},
1533
new Remover() { void remove(NavigableMap m, Object k, Object v) {
1534
check(m.descendingKeySet().subSet(86, true, -86, false)
1535
.remove(k)); }},
1536
};
1537
1538
for (NavigableMapView view : views) {
1539
for (Remover remover : removers) {
1540
try {
1541
m.clear();
1542
equalMaps(m, emptyMap);
1543
equal(m.put(1, 2), null);
1544
equalMaps(m, singletonMap);
1545
NavigableMap v = view.view(m);
1546
remover.remove(v, 1, 2);
1547
equalMaps(m, emptyMap);
1548
} catch (Throwable t) { unexpected(t); }
1549
}
1550
}
1551
}
1552
1553
private static void testNavigableMap(NavigableMap<Integer,Integer> m)
1554
{
1555
clear(m);
1556
checkNavigableMapKeys(m, 1, null, null, null, null);
1557
1558
equal(m.put(1, 2), null);
1559
equal(m.put(3, 4), null);
1560
equal(m.put(5, 9), null);
1561
1562
equal(m.put(1, 2), 2);
1563
equal(m.put(3, 4), 4);
1564
equal(m.put(5, 6), 9);
1565
1566
checkNavigableMapKeys(m, 0, null, null, 1, 1);
1567
checkNavigableMapKeys(m, 1, null, 1, 1, 3);
1568
checkNavigableMapKeys(m, 2, 1, 1, 3, 3);
1569
checkNavigableMapKeys(m, 3, 1, 3, 3, 5);
1570
checkNavigableMapKeys(m, 5, 3, 5, 5, null);
1571
checkNavigableMapKeys(m, 6, 5, 5, null, null);
1572
1573
for (final Iterator<Integer> it :
1574
(Iterator<Integer>[])
1575
new Iterator<?>[] {
1576
m.descendingKeySet().iterator(),
1577
m.navigableKeySet().descendingIterator()}) {
1578
equalNext(it, 5);
1579
equalNext(it, 3);
1580
equalNext(it, 1);
1581
check(! it.hasNext());
1582
THROWS(NoSuchElementException.class, () -> it.next());
1583
}
1584
1585
{
1586
final Iterator<Map.Entry<Integer,Integer>> it
1587
= m.descendingMap().entrySet().iterator();
1588
check(it.hasNext()); equal(it.next().getKey(), 5);
1589
check(it.hasNext()); equal(it.next().getKey(), 3);
1590
check(it.hasNext()); equal(it.next().getKey(), 1);
1591
check(! it.hasNext());
1592
THROWS(NoSuchElementException.class, () -> it.next());
1593
}
1594
1595
prepMapForDescItrTests(m);
1596
checkDescItrRmFirst(m.keySet(), m.navigableKeySet().descendingIterator());
1597
prepMapForDescItrTests(m);
1598
checkDescItrRmMid(m.keySet(), m.navigableKeySet().descendingIterator());
1599
prepMapForDescItrTests(m);
1600
checkDescItrRmLast(m.keySet(), m.navigableKeySet().descendingIterator());
1601
1602
prepMapForDescItrTests(m);
1603
checkDescItrRmFirst(m.keySet(), m.descendingMap().keySet().iterator());
1604
prepMapForDescItrTests(m);
1605
checkDescItrRmMid(m.keySet(), m.descendingMap().keySet().iterator());
1606
prepMapForDescItrTests(m);
1607
checkDescItrRmLast(m.keySet(), m.descendingMap().keySet().iterator());
1608
1609
prepMapForDescItrTests(m);
1610
checkDescItrRmFirst(m.keySet(), m.descendingKeySet().iterator());
1611
prepMapForDescItrTests(m);
1612
checkDescItrRmMid(m.keySet(), m.descendingKeySet().iterator());
1613
prepMapForDescItrTests(m);
1614
checkDescItrRmLast(m.keySet(), m.descendingKeySet().iterator());
1615
1616
prepMapForDescItrTests(m);
1617
checkDescItrRmFirst(m.values(), m.descendingMap().values().iterator());
1618
prepMapForDescItrTests(m);
1619
checkDescItrRmMid(m.values(), m.descendingMap().values().iterator());
1620
prepMapForDescItrTests(m);
1621
checkDescItrRmLast(m.values(), m.descendingMap().values().iterator());
1622
1623
prepMapForDescItrTests(m);
1624
checkDescItrRmFirst((Collection)m.entrySet(),
1625
m.descendingMap().entrySet().iterator());
1626
prepMapForDescItrTests(m);
1627
checkDescItrRmMid((Collection)m.entrySet(),
1628
m.descendingMap().entrySet().iterator());
1629
prepMapForDescItrTests(m);
1630
checkDescItrRmLast((Collection)m.entrySet(),
1631
m.descendingMap().entrySet().iterator());
1632
}
1633
1634
private static void testNavigableSet(NavigableSet<Integer> s) {
1635
clear(s);
1636
checkNavigableSetKeys(s, 1, null, null, null, null);
1637
1638
check(s.add(1));
1639
check(s.add(3));
1640
check(s.add(5));
1641
1642
check(! s.add(1));
1643
check(! s.add(3));
1644
check(! s.add(5));
1645
1646
checkNavigableSetKeys(s, 0, null, null, 1, 1);
1647
checkNavigableSetKeys(s, 1, null, 1, 1, 3);
1648
checkNavigableSetKeys(s, 2, 1, 1, 3, 3);
1649
checkNavigableSetKeys(s, 3, 1, 3, 3, 5);
1650
checkNavigableSetKeys(s, 5, 3, 5, 5, null);
1651
checkNavigableSetKeys(s, 6, 5, 5, null, null);
1652
1653
for (final Iterator<Integer> it :
1654
(Iterator<Integer>[])
1655
new Iterator<?>[] {
1656
s.descendingIterator(),
1657
s.descendingSet().iterator()}) {
1658
equalNext(it, 5);
1659
equalNext(it, 3);
1660
equalNext(it, 1);
1661
check(! it.hasNext());
1662
THROWS(NoSuchElementException.class, () -> it.next());
1663
}
1664
1665
prepSetForDescItrTests(s);
1666
checkDescItrRmFirst(s, s.descendingIterator());
1667
prepSetForDescItrTests(s);
1668
checkDescItrRmMid(s, s.descendingIterator());
1669
prepSetForDescItrTests(s);
1670
checkDescItrRmLast(s, s.descendingIterator());
1671
1672
prepSetForDescItrTests(s);
1673
checkDescItrRmFirst(s, s.descendingSet().iterator());
1674
prepSetForDescItrTests(s);
1675
checkDescItrRmMid(s, s.descendingSet().iterator());
1676
prepSetForDescItrTests(s);
1677
checkDescItrRmLast(s, s.descendingSet().iterator());
1678
}
1679
1680
private static void prepSetForDescItrTests(Set s) {
1681
clear(s);
1682
check(s.add(1));
1683
check(s.add(3));
1684
check(s.add(5));
1685
}
1686
1687
private static void prepMapForDescItrTests(Map m) {
1688
clear(m);
1689
equal(m.put(1, 2), null);
1690
equal(m.put(3, 4), null);
1691
equal(m.put(5, 9), null);
1692
}
1693
1694
//--------------------------------------------------------------------
1695
// Check behavior of descending iterator when first element is removed
1696
//--------------------------------------------------------------------
1697
private static <T> void checkDescItrRmFirst(Collection<T> ascColl,
1698
Iterator<T> descItr) {
1699
T[] expected = (T[]) ascColl.toArray();
1700
int idx = expected.length -1;
1701
1702
equalNext(descItr, expected[idx--]);
1703
descItr.remove();
1704
while (idx >= 0 && descItr.hasNext()) {
1705
equalNext(descItr, expected[idx--]);
1706
}
1707
equal(descItr.hasNext(), false);
1708
equal(idx, -1);
1709
}
1710
1711
//-----------------------------------------------------------------------
1712
// Check behavior of descending iterator when a middle element is removed
1713
//-----------------------------------------------------------------------
1714
private static <T> void checkDescItrRmMid(Collection<T> ascColl,
1715
Iterator<T> descItr) {
1716
T[] expected = (T[]) ascColl.toArray();
1717
int idx = expected.length -1;
1718
1719
while (idx >= expected.length / 2) {
1720
equalNext(descItr, expected[idx--]);
1721
}
1722
descItr.remove();
1723
while (idx >= 0 && descItr.hasNext()) {
1724
equalNext(descItr, expected[idx--]);
1725
}
1726
equal(descItr.hasNext(), false);
1727
equal(idx, -1);
1728
}
1729
1730
//-----------------------------------------------------------------------
1731
// Check behavior of descending iterator when the last element is removed
1732
//-----------------------------------------------------------------------
1733
private static <T> void checkDescItrRmLast(Collection<T> ascColl,
1734
Iterator<T> descItr) {
1735
T[] expected = (T[]) ascColl.toArray();
1736
int idx = expected.length -1;
1737
1738
while (idx >= 0 && descItr.hasNext()) {
1739
equalNext(descItr, expected[idx--]);
1740
}
1741
equal(idx, -1);
1742
equal(descItr.hasNext(), false);
1743
descItr.remove();
1744
equal(ascColl.contains(expected[0]), false);
1745
}
1746
1747
//--------------------- Infrastructure ---------------------------
1748
static volatile int passed = 0, failed = 0;
1749
static void pass() { passed++; }
1750
static void fail() { failed++; Thread.dumpStack(); }
1751
static void fail(String msg) { System.out.println(msg); fail(); }
1752
static void unexpected(Throwable t) { failed++; t.printStackTrace(); }
1753
static void check(boolean cond) { if (cond) pass(); else fail(); }
1754
static void equal(Object x, Object y) {
1755
if (x == null ? y == null : x.equals(y)) pass();
1756
else {System.out.println(x + " not equal to " + y); fail();}}
1757
static void equal(Object x, Object y, String msg) {
1758
if (x == null ? y == null : x.equals(y)) pass();
1759
else {System.out.println(x + " not equal to " + y + " : " + msg); fail();}}
1760
static void equal2(Object x, Object y) {equal(x, y); equal(y, x);}
1761
public static void main(String[] args) throws Throwable {
1762
try { realMain(args); } catch (Throwable t) { unexpected(t); }
1763
1764
System.out.printf("%nPassed = %d, failed = %d%n%n", passed, failed);
1765
if (failed > 0) throw new Exception("Some tests failed");
1766
}
1767
interface Fun {void f() throws Throwable;}
1768
private static void THROWS(Class<? extends Throwable> k, Fun... fs) {
1769
for (Fun f : fs)
1770
try { f.f(); fail("Expected " + k.getName() + " not thrown"); }
1771
catch (Throwable t) {
1772
if (k.isAssignableFrom(t.getClass())) pass();
1773
else unexpected(t);}}
1774
static byte[] serializedForm(Object obj) {
1775
try {
1776
ByteArrayOutputStream baos = new ByteArrayOutputStream();
1777
new ObjectOutputStream(baos).writeObject(obj);
1778
return baos.toByteArray();
1779
} catch (IOException e) { throw new Error(e); }}
1780
static Object readObject(byte[] bytes)
1781
throws IOException, ClassNotFoundException {
1782
InputStream is = new ByteArrayInputStream(bytes);
1783
return new ObjectInputStream(is).readObject();}
1784
@SuppressWarnings("unchecked")
1785
static <T> T serialClone(T obj) {
1786
try { return (T) readObject(serializedForm(obj)); }
1787
catch (Exception e) { throw new Error(e); }}
1788
private static class NewAbstractCollection<E> extends AbstractCollection<E> {
1789
ArrayList<E> list = new ArrayList<>();
1790
public boolean remove(Object obj) {
1791
return list.remove(obj);
1792
}
1793
public boolean add(E e) {
1794
return list.add(e);
1795
}
1796
public Iterator<E> iterator() {
1797
return list.iterator();
1798
}
1799
public int size() {
1800
return list.size();
1801
}
1802
}
1803
private static class NewAbstractSet<E> extends AbstractSet<E> {
1804
HashSet<E> set = new HashSet<>();
1805
public boolean remove(Object obj) {
1806
return set.remove(obj);
1807
}
1808
public boolean add(E e) {
1809
return set.add(e);
1810
}
1811
public Iterator<E> iterator() {
1812
return set.iterator();
1813
}
1814
public int size() {
1815
return set.size();
1816
}
1817
}
1818
1819
}
1820
1821