Can get, put & remove elemetn in HashMap without iteration cause ConcurrentModificationException?

混江龙づ霸主 提交于 2019-12-23 23:52:47

问题


I have a static hashMap, shared with multiple threads. I am not iterating the map at all but just uses the get, put, remove. Is it safe from ConcurrentModificationException ?

The method looks like this

private static Map<Long, Integer> TRACKER = new HashMap<Long,Integer>();
public static void track(Long tid, boolean b) {
        if (b) {
            if (TRACKER.containsKey(tid)) {
                TRACKER.put(tid, TRACKER.get(tid) + 1);
            } else {
                TRACKER.put(tid, 1);
            }
        } else {
            Integer n = TRACKER.get(tid);
            if (n != null) {
                n = n -1;
                if (n == 0) {
                    TRACKER.remove(tid);
                } else {
                    TRACKER.put(tid, n);
                }
            }
        }
    }

回答1:


Is it safe from ConcurrentModificationException?

It is safe from ConcurrentModificationException. That exception is only thrown by methods that iterate (in some sense) the map or one of its views using a conventional iterator or a spliterator.

However, since HashMap is not a thread-safe class, if you use it from multiple threads without proper external external synchronization, bad things can happen. These include (in order of increasing badness)

  1. The size() method reporting the wrong value.
  2. Entries mysteriously disappearing, either temporarily or permanently.
  3. Possible NPEs and other unchecked exceptions.
  4. Possible infinite loops due to an unfortunate sequence of operations by multiple threads creating a loop in a hash chain.

Your example code is unsafe ... but you won't get a "fast fail" ConcurrentModificationException. Instead you are likely to get inexplicable errors at "random" times that are difficult to reproduce.




回答2:


If multiple threads are performing get, put & remove operations on a HashMap, without proper synchronization, some bad things like size() reporting missing / lost entries, unexpected NPEs ... even infinite loops may happen.

HashMap documentation says -

Note that this implementation is not synchronized. If multiple threads access a hash map concurrently, and at least one of the threads modifies the map structurally, it must be synchronized externally. (A structural modification is any operation that adds or deletes one or more mappings; merely changing the value associated with a key that an instance already contains is not a structural modification.) ...

Thanks Stephen.



来源:https://stackoverflow.com/questions/52213393/can-get-put-remove-elemetn-in-hashmap-without-iteration-cause-concurrentmodif

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!