Showing posts from May, 2015

Puzzler: nested computeIfAbsent

Overview The Java 8 libraries have a new method on map, computeIfAbsent.  This is very useful way to turn your Map into a cache of objects associated with a key. However, there is a combination you might not have considered; what happens if you call computeIfAbsent inside itself. map.computeIfAbsent(Key. Hello , s -> { map.computeIfAbsent(Key. Hello , t -> 1 ); return 2 ; }); enum Key { Hello } While this might seem like a strange thing to do in simple cases, in more complex code you could do this by accident (as I did this afternoon)  So what happens?  Well it depends on the collection you are using. HashMap: {Hello=2} WeakHashMap: {Hello=2} TreeMap: {Hello=2} IdentityHashMap: {Hello=2} EnumMap: {Hello=2} Hashtable: {Hello=2, Hello=1} LinkedHashMap: {Hello=1, Hello=2} ConcurrentSkipListMap: {Hello=1} ConcurrentHashMap:  Note: ConcurrentHashMap never returns.  It's locking doesn't appear to be re-entrant. ConcurrentSkipList