Java multi-threading atomic reference assignment

前端 未结 4 1218
别跟我提以往
别跟我提以往 2020-12-08 03:02

I have a cache which I implemented using a simeple HashMap. like -

HashMap cache = new HashMap();

相关标签:
4条回答
  • 2020-12-08 03:39

    It is not safe without a proper memory barrier.

    One would think that the assignment of cache (cache = newCache) would happen after the steps to populate the cache. However, other threads may suffer from reordering of these statements so that the assignment may appear to happen before populating the cache. Thus, it is possible to grab the new cache before it's fully constructed or even worse see a ConcurrentModificationException.

    You need to enforce the happens-before relationship to prevent this reordering, and declaring the cache as volatile would achieve that.

    0 讨论(0)
  • 2020-12-08 03:42

    What about CopyOnWrite.. collections:

    java.util.concurrent.CopyOnWriteArraySet
    java.util.concurrent.CopyOnWriteArraySet
    and org.apache.mina.util.CopyOnWriteMap
    

    They can be a good match in your case and they are thread-safe.

    0 讨论(0)
  • 2020-12-08 03:44

    Seems to be OK. Be sure refreshCache is not called too frequently or mark as synchronized.

    0 讨论(0)
  • 2020-12-08 03:48

    You should mark the cache as volatile.

    While you note that other threads may continue using a stale cache for "a long time" you should note that, without a synchronization edge, they are likely to continue using the stale cache forever. That's probably not the desired behavior.

    In order of preference (mostly due to readability):

    • Update the field in a synchronized method
    • Use AtomicReference<Map<>>
    • Use volatile

    See also this question.

    0 讨论(0)
提交回复
热议问题