ViewVC Help
View File | Revision Log | Show Annotations | Download File | Root Listing
root/jsr166/jsr166/src/test/tck/ConcurrentHashMap8Test.java
(Generate patch)

Comparing jsr166/src/test/tck/ConcurrentHashMap8Test.java (file contents):
Revision 1.12 by dl, Sun Jul 21 22:24:18 2013 UTC vs.
Revision 1.37 by jsr166, Mon May 28 21:36:41 2018 UTC

# Line 4 | Line 4
4   * http://creativecommons.org/publicdomain/zero/1.0/
5   */
6  
7 < import junit.framework.*;
8 < import java.util.*;
9 < import java.util.function.*;
10 < import java.util.concurrent.atomic.LongAdder;
7 > import static java.util.Spliterator.CONCURRENT;
8 > import static java.util.Spliterator.DISTINCT;
9 > import static java.util.Spliterator.NONNULL;
10 >
11 > import java.util.AbstractMap;
12 > import java.util.Arrays;
13 > import java.util.Collection;
14 > import java.util.Iterator;
15 > import java.util.Map;
16 > import java.util.NoSuchElementException;
17 > import java.util.Set;
18 > import java.util.Spliterator;
19 > import java.util.concurrent.ExecutorService;
20 > import java.util.concurrent.Executors;
21   import java.util.concurrent.ConcurrentHashMap;
22 < import java.util.concurrent.ConcurrentHashMap.KeySetView;
22 > import java.util.concurrent.atomic.LongAdder;
23 > import java.util.function.BiFunction;
24 >
25 > import junit.framework.Test;
26 > import junit.framework.TestSuite;
27  
28   public class ConcurrentHashMap8Test extends JSR166TestCase {
29      public static void main(String[] args) {
30 <        junit.textui.TestRunner.run(suite());
30 >        main(suite(), args);
31      }
32      public static Test suite() {
33          return new TestSuite(ConcurrentHashMap8Test.class);
# Line 49 | Line 63 | public class ConcurrentHashMap8Test exte
63       */
64      public void testComputeIfAbsent() {
65          ConcurrentHashMap map = map5();
66 <        map.computeIfAbsent(six, (x) -> "Z");
66 >        map.computeIfAbsent(six, x -> "Z");
67          assertTrue(map.containsKey(six));
68      }
69  
70      /**
71 <     * computeIfAbsent does not replace  if the key is already present
71 >     * computeIfAbsent does not replace if the key is already present
72       */
73      public void testComputeIfAbsent2() {
74          ConcurrentHashMap map = map5();
75 <        assertEquals("A", map.computeIfAbsent(one, (x) -> "Z"));
75 >        assertEquals("A", map.computeIfAbsent(one, x -> "Z"));
76      }
77  
78      /**
# Line 66 | Line 80 | public class ConcurrentHashMap8Test exte
80       */
81      public void testComputeIfAbsent3() {
82          ConcurrentHashMap map = map5();
83 <        map.computeIfAbsent(six, (x) -> null);
83 >        map.computeIfAbsent(six, x -> null);
84          assertFalse(map.containsKey(six));
85      }
86  
87      /**
88 <     * computeIfPresent does not replace  if the key is already present
88 >     * computeIfPresent does not replace if the key is already present
89       */
90      public void testComputeIfPresent() {
91          ConcurrentHashMap map = map5();
# Line 88 | Line 102 | public class ConcurrentHashMap8Test exte
102      }
103  
104      /**
105 <     * compute does not replace  if the function returns null
105 >     * compute does not replace if the function returns null
106       */
107      public void testCompute() {
108          ConcurrentHashMap map = map5();
# Line 150 | Line 164 | public class ConcurrentHashMap8Test exte
164          Set<Integer> a = ConcurrentHashMap.<Integer>newKeySet();
165          assertTrue(a.isEmpty());
166          for (int i = 0; i < n; i++)
167 <            a.add(i);
168 <        assertFalse(a.isEmpty());
167 >            assertTrue(a.add(i));
168 >        assertEquals(n == 0, a.isEmpty());
169          assertEquals(n, a.size());
170          return a;
171      }
# Line 159 | Line 173 | public class ConcurrentHashMap8Test exte
173      static Set populatedSet(Integer[] elements) {
174          Set<Integer> a = ConcurrentHashMap.<Integer>newKeySet();
175          assertTrue(a.isEmpty());
176 <        for (int i = 0; i < elements.length; i++)
177 <            a.add(elements[i]);
176 >        for (Integer element : elements)
177 >            assertTrue(a.add(element));
178          assertFalse(a.isEmpty());
179          assertEquals(elements.length, a.size());
180          return a;
181      }
182  
183 <    /*
183 >    /**
184       * replaceAll replaces all matching values.
185       */
186      public void testReplaceAll() {
187          ConcurrentHashMap<Integer, String> map = map5();
188 <        map.replaceAll((x, y) -> {return x > 3 ? "Z" : y;});
188 >        map.replaceAll((x, y) -> (x > 3) ? "Z" : y);
189          assertEquals("A", map.get(one));
190          assertEquals("B", map.get(two));
191          assertEquals("C", map.get(three));
# Line 196 | Line 210 | public class ConcurrentHashMap8Test exte
210          Set set1 = map.keySet();
211          Set set2 = map.keySet(true);
212          set2.add(six);
213 <        assertTrue(((KeySetView)set2).getMap() == map);
214 <        assertTrue(((KeySetView)set1).getMap() == map);
213 >        assertSame(map, ((ConcurrentHashMap.KeySetView)set2).getMap());
214 >        assertSame(map, ((ConcurrentHashMap.KeySetView)set1).getMap());
215          assertEquals(set2.size(), map.size());
216          assertEquals(set1.size(), map.size());
217          assertTrue((Boolean)map.get(six));
# Line 209 | Line 223 | public class ConcurrentHashMap8Test exte
223          assertFalse(set2.contains(six));
224      }
225  
212
226      /**
227       * keySet.addAll adds each element from the given collection
228       */
229      public void testAddAll() {
230          Set full = populatedSet(3);
231 <        Vector v = new Vector();
232 <        v.add(three);
233 <        v.add(four);
221 <        v.add(five);
222 <        full.addAll(v);
231 >        assertTrue(full.addAll(Arrays.asList(three, four, five)));
232 >        assertEquals(6, full.size());
233 >        assertFalse(full.addAll(Arrays.asList(three, four, five)));
234          assertEquals(6, full.size());
235      }
236  
# Line 229 | Line 240 | public class ConcurrentHashMap8Test exte
240       */
241      public void testAddAll2() {
242          Set full = populatedSet(3);
243 <        Vector v = new Vector();
244 <        v.add(three);
245 <        v.add(four);
246 <        v.add(one); // will not add this element
236 <        full.addAll(v);
243 >        // "one" is duplicate and will not be added
244 >        assertTrue(full.addAll(Arrays.asList(three, four, one)));
245 >        assertEquals(5, full.size());
246 >        assertFalse(full.addAll(Arrays.asList(three, four, one)));
247          assertEquals(5, full.size());
248      }
249  
# Line 242 | Line 252 | public class ConcurrentHashMap8Test exte
252       */
253      public void testAdd2() {
254          Set full = populatedSet(3);
255 <        full.add(one);
255 >        assertFalse(full.add(one));
256          assertEquals(3, full.size());
257      }
258  
# Line 251 | Line 261 | public class ConcurrentHashMap8Test exte
261       */
262      public void testAdd3() {
263          Set full = populatedSet(3);
264 <        full.add(three);
264 >        assertTrue(full.add(three));
265 >        assertTrue(full.contains(three));
266 >        assertFalse(full.add(three));
267          assertTrue(full.contains(three));
268      }
269  
270 +    /**
271 +     * keySet.add throws UnsupportedOperationException if no default
272 +     * mapped value
273 +     */
274 +    public void testAdd4() {
275 +        Set full = map5().keySet();
276 +        try {
277 +            full.add(three);
278 +            shouldThrow();
279 +        } catch (UnsupportedOperationException success) {}
280 +    }
281 +
282 +    /**
283 +     * keySet.add throws NullPointerException if the specified key is
284 +     * null
285 +     */
286 +    public void testAdd5() {
287 +        Set full = populatedSet(3);
288 +        try {
289 +            full.add(null);
290 +            shouldThrow();
291 +        } catch (NullPointerException success) {}
292 +    }
293 +
294 +    /**
295 +     * KeySetView.getMappedValue returns the map's mapped value
296 +     */
297 +    public void testGetMappedValue() {
298 +        ConcurrentHashMap map = map5();
299 +        assertNull(map.keySet().getMappedValue());
300 +        try {
301 +            map.keySet(null);
302 +            shouldThrow();
303 +        } catch (NullPointerException success) {}
304 +        ConcurrentHashMap.KeySetView set = map.keySet(one);
305 +        assertFalse(set.add(one));
306 +        assertTrue(set.add(six));
307 +        assertTrue(set.add(seven));
308 +        assertSame(one, set.getMappedValue());
309 +        assertNotSame(one, map.get(one));
310 +        assertSame(one, map.get(six));
311 +        assertSame(one, map.get(seven));
312 +    }
313 +
314 +    void checkSpliteratorCharacteristics(Spliterator<?> sp,
315 +                                         int requiredCharacteristics) {
316 +        assertEquals(requiredCharacteristics,
317 +                     requiredCharacteristics & sp.characteristics());
318 +    }
319  
320 <      /**
321 <      * keySet.add throws UnsupportedOperationException if no default
322 <      * mapped value
323 <      */
324 <     public void testAdd4() {
325 <         Set full = map5().keySet();
326 <         try {
327 <             full.add(three);
328 <             shouldThrow();
329 <         } catch (UnsupportedOperationException e){}
330 <     }
331 <    
332 <     /**
333 <      * keySet.add throws NullPointerException if the specified key is
334 <      * null
335 <      */
336 <     public void testAdd5() {
276 <         Set full = populatedSet(3);
277 <         try {
278 <             full.add(null);
279 <             shouldThrow();
280 <         } catch (NullPointerException e){}
281 <     }
282 <    
283 <     /**
284 <      * KeySetView.getMappedValue returns the map's mapped value
285 <      */
286 <     public void testGetMappedValue() {
287 <         ConcurrentHashMap map = map5();
288 <         assertNull(map.keySet().getMappedValue());
289 <         try {
290 <             map.keySet(null);
291 <             shouldThrow();
292 <         } catch (NullPointerException e) {}
293 <         KeySetView set = map.keySet(one);
294 <         set.add(one);
295 <         set.add(six);
296 <         set.add(seven);
297 <         assertTrue(set.getMappedValue() == one);
298 <         assertTrue(map.get(one) != one);
299 <         assertTrue(map.get(six) == one);
300 <         assertTrue(map.get(seven) == one);
301 <     }
302 <    
303 <     /**
304 <      * KeySetView.spliterator returns spliterator over the elements in this set
305 <      */
306 <     public void testKeySetSpliterator() {
307 <         LongAdder adder = new LongAdder();
308 <         ConcurrentHashMap map = map5();
309 <         Set set = map.keySet();
310 <         Spliterator<Integer> sp = set.spliterator();
311 <         assertEquals(sp.estimateSize(), map.size());
312 <         Spliterator<Integer> sp2 = sp.trySplit();
313 <         sp.forEachRemaining((Integer x) -> adder.add(x.longValue()));
314 <         long v = adder.sumThenReset();
315 <         sp2.forEachRemaining((Integer x) -> adder.add(x.longValue()));
316 <         long v2 = adder.sum();
317 <         assertEquals(v + v2, 15);
318 <     }
319 <
320 >    /**
321 >     * KeySetView.spliterator returns spliterator over the elements in this set
322 >     */
323 >    public void testKeySetSpliterator() {
324 >        LongAdder adder = new LongAdder();
325 >        ConcurrentHashMap map = map5();
326 >        Set set = map.keySet();
327 >        Spliterator<Integer> sp = set.spliterator();
328 >        checkSpliteratorCharacteristics(sp, CONCURRENT | DISTINCT | NONNULL);
329 >        assertEquals(sp.estimateSize(), map.size());
330 >        Spliterator<Integer> sp2 = sp.trySplit();
331 >        sp.forEachRemaining((Integer x) -> adder.add(x.longValue()));
332 >        long v = adder.sumThenReset();
333 >        sp2.forEachRemaining((Integer x) -> adder.add(x.longValue()));
334 >        long v2 = adder.sum();
335 >        assertEquals(v + v2, 15);
336 >    }
337  
338      /**
339       * keyset.clear removes all elements from the set
# Line 358 | Line 375 | public class ConcurrentHashMap8Test exte
375       * KeySet.containsAll returns true for collections with subset of elements
376       */
377      public void testContainsAll() {
378 <        Set full = populatedSet(3);
379 <        Vector v = new Vector();
380 <        v.add(one);
381 <        v.add(two);
382 <        assertTrue(full.containsAll(v));
383 <        v.add(six);
367 <        assertFalse(full.containsAll(v));
378 >        Collection full = populatedSet(3);
379 >        assertTrue(full.containsAll(Arrays.asList()));
380 >        assertTrue(full.containsAll(Arrays.asList(one)));
381 >        assertTrue(full.containsAll(Arrays.asList(one, two)));
382 >        assertFalse(full.containsAll(Arrays.asList(one, two, six)));
383 >        assertFalse(full.containsAll(Arrays.asList(six)));
384      }
385  
386      /**
387       * KeySet.isEmpty is true when empty, else false
388       */
389      public void testIsEmpty() {
390 <        Set empty = ConcurrentHashMap.newKeySet();
391 <        Set full = populatedSet(3);
376 <        assertTrue(empty.isEmpty());
377 <        assertFalse(full.isEmpty());
390 >        assertTrue(populatedSet(0).isEmpty());
391 >        assertFalse(populatedSet(3).isEmpty());
392      }
393  
394      /**
# Line 393 | Line 407 | public class ConcurrentHashMap8Test exte
407          Integer[] elements = new Integer[size];
408          for (int i = 0; i < size; i++)
409              elements[i] = i;
410 <        Collections.shuffle(Arrays.asList(elements));
410 >        shuffle(elements);
411          Collection<Integer> full = populatedSet(elements);
412  
413          Iterator it = full.iterator();
# Line 401 | Line 415 | public class ConcurrentHashMap8Test exte
415              assertTrue(it.hasNext());
416              it.next();
417          }
418 <        assertFalse(it.hasNext());
419 <        try {
420 <            it.next();
421 <            shouldThrow();
422 <        } catch (NoSuchElementException success) {}
418 >        assertIteratorExhausted(it);
419 >    }
420 >
421 >    /**
422 >     * iterator of empty collections has no elements
423 >     */
424 >    public void testEmptyIterator() {
425 >        assertIteratorExhausted(ConcurrentHashMap.newKeySet().iterator());
426 >        assertIteratorExhausted(new ConcurrentHashMap().entrySet().iterator());
427 >        assertIteratorExhausted(new ConcurrentHashMap().values().iterator());
428 >        assertIteratorExhausted(new ConcurrentHashMap().keySet().iterator());
429      }
430  
431      /**
# Line 439 | Line 459 | public class ConcurrentHashMap8Test exte
459       */
460      public void testRemoveAll() {
461          Set full = populatedSet(3);
462 <        Vector v = new Vector();
463 <        v.add(one);
464 <        v.add(two);
445 <        full.removeAll(v);
462 >        assertTrue(full.removeAll(Arrays.asList(one, two)));
463 >        assertEquals(1, full.size());
464 >        assertFalse(full.removeAll(Arrays.asList(one, two)));
465          assertEquals(1, full.size());
466      }
467  
# Line 478 | Line 497 | public class ConcurrentHashMap8Test exte
497          Integer[] elements = new Integer[size];
498          for (int i = 0; i < size; i++)
499              elements[i] = i;
500 <        Collections.shuffle(Arrays.asList(elements));
500 >        shuffle(elements);
501          Collection<Integer> full = populatedSet(elements);
502  
503          assertTrue(Arrays.asList(elements).containsAll(Arrays.asList(full.toArray())));
# Line 498 | Line 517 | public class ConcurrentHashMap8Test exte
517          a = new Integer[0];
518          assertSame(a, empty.toArray(a));
519  
520 <        a = new Integer[size/2];
520 >        a = new Integer[size / 2];
521          Arrays.fill(a, 42);
522          assertSame(a, empty.toArray(a));
523          assertNull(a[0]);
# Line 508 | Line 527 | public class ConcurrentHashMap8Test exte
527          Integer[] elements = new Integer[size];
528          for (int i = 0; i < size; i++)
529              elements[i] = i;
530 <        Collections.shuffle(Arrays.asList(elements));
530 >        shuffle(elements);
531          Collection<Integer> full = populatedSet(elements);
532  
533          Arrays.fill(a, 42);
# Line 524 | Line 543 | public class ConcurrentHashMap8Test exte
543      }
544  
545      /**
546 <     * A deserialized serialized set is equal
546 >     * A deserialized/reserialized set equals original
547       */
548      public void testSerialization() throws Exception {
549          int size = 20;
# Line 533 | Line 552 | public class ConcurrentHashMap8Test exte
552  
553          assertNotSame(x, y);
554          assertEquals(x.size(), y.size());
536        assertEquals(x.toString(), y.toString());
537        assertTrue(Arrays.equals(x.toArray(), y.toArray()));
555          assertEquals(x, y);
556          assertEquals(y, x);
557      }
# Line 986 | Line 1003 | public class ConcurrentHashMap8Test exte
1003      public void testSearchValuesSequentially() {
1004          ConcurrentHashMap<Long, Long> m = longMap();
1005          Long r;
1006 <        r = m.searchValues(Long.MAX_VALUE, (Long x) -> x.longValue() == (long)(SIZE/2)? x : null);
1006 >        r = m.searchValues(Long.MAX_VALUE,
1007 >            (Long x) -> (x.longValue() == (long)(SIZE/2)) ? x : null);
1008          assertEquals((long)r, (long)(SIZE/2));
1009 <        r = m.searchValues(Long.MAX_VALUE, (Long x) -> x.longValue() < 0L ? x : null);
1009 >        r = m.searchValues(Long.MAX_VALUE,
1010 >            (Long x) -> (x.longValue() < 0L) ? x : null);
1011          assertNull(r);
1012      }
1013  
# Line 1070 | Line 1089 | public class ConcurrentHashMap8Test exte
1089          assertNull(r);
1090      }
1091  
1092 +    /**
1093 +     * Tests performance of computeIfAbsent when the element is present.
1094 +     * See JDK-8161372
1095 +     * ant -Djsr166.tckTestClass=ConcurrentHashMapTest -Djsr166.methodFilter=testcomputeIfAbsent_performance -Djsr166.expensiveTests=true tck
1096 +     */
1097 +    public void testcomputeIfAbsent_performance() {
1098 +        final int mapSize = 20;
1099 +        final int iterations = expensiveTests ? (1 << 23) : mapSize * 2;
1100 +        final int threads = expensiveTests ? 10 : 2;
1101 +        final ConcurrentHashMap<Integer, Integer> map = new ConcurrentHashMap<>();
1102 +        for (int i = 0; i < mapSize; i++)
1103 +            map.put(i, i);
1104 +        final ExecutorService pool = Executors.newFixedThreadPool(2);
1105 +        try (PoolCleaner cleaner = cleaner(pool)) {
1106 +            Runnable r = new CheckedRunnable() {
1107 +                public void realRun() {
1108 +                    int result = 0;
1109 +                    for (int i = 0; i < iterations; i++)
1110 +                        result += map.computeIfAbsent(i % mapSize, k -> k + k);
1111 +                    if (result == -42) throw new Error();
1112 +                }};
1113 +            for (int i = 0; i < threads; i++)
1114 +                pool.execute(r);
1115 +        }
1116 +    }
1117 +
1118   }

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines