Use of ConcurrentHashMap eliminates data-visibility troubles?

こ雲淡風輕ζ 提交于 2019-12-06 11:40:40

问题


I've read through Java Concurrency in Practice and am left with this question: when I use a ConcurrentHashMap, what data concurrency issues discussed in Part One of the book do I still need to worry about? Here are a couple of examples from one of my programs:

1. Current position of a trader (a shared integer where 'integer' is the mathematical term)

This number represents what a trader object currently owns and defines its state. It must read its position to know what to do (look to start a new position, or manage the current one). Trader methods run on their own thread.

A broker object is in charge of setting the trader's position. It will set the position each time one of the trader's orders is filled. Broker methods run on their own thread.

Both the trader and broker are in the same package. Position is implemented as a package-private static ConcurrentHashMap. The keys are id's of the trader objects. The values are Integer.

External to the package is the application. It gets the traders' positions indirectly with a public getter.

Positions will change at most once every few minutes, so the broker won't touch the map very often. However, the trader and application will frequently read. In addition we often have several traders reading the map concurrently.

So using a ConcurrentHashMap this way, I don't have to work about locking and data visibility? The ConcurrentHashMap takes care of everything?

2. The market (bid, ask, last prices)

Pretty much the same situation as position, except now the broker will very frequently update the prices (up to 10 updates a second during busy times; normally a few times a second). The trader and application still do frequent reads. The map keys now are codes indicating which stock or future, and the values are objects which hold the market prices.

It seems to work okay, but after reading JCIP, I realize the program can still be broken if things are not implemented correctly. The book talks about the ConcurrentHashMap but doesn't explicitly tell me what issues from Part I we no longer have to address manually. It appears that I don't have to synchronize anything in this case. Is that correct?


回答1:


So using a ConcurrentHashMap this way, I don't have to work about locking and data visibility? The ConcurrentHashMap takes care of everything?

This depends on what is in the Map, if I read your example correctly the situation looks like this

static final ConcurrentMap<Integer,Integer> map = ...

class Trader{

  public int doRead(){
      map.get(someId);
   }
}
class Broker{
   public void doWrite(){
      map.put(someId,someValue);
   }
}

If that is the case, then yes all the concurrency is taken care of.

However if the map looks like

static final ConcurrentMap<Integer,Trader> map = ..

    class Broker{
       public void doWrite(){
          map.get(someId).setPosition(somePosition);
       }
    }

This is NOT thread safe, even though the ConcurrentHashMap locks when you put, all concurrent access of objects at this point must handle their own synchronization.




回答2:


Yes, ConcurrentHashMap takes care of visibility and locking as long as:

  • values held by map are immutable. Seems to be true in your description, given that your prices objects are immutable;
  • you don't have operations on map which must be atomic and can't be expressed as single calls to map's API. For example if you need operation like 'read value from map, perform calculation, and put the result back on the map' to be atomic, you still need to hold explicit lock during this operation, or, better yet, change application so you only use atomic operations of map API such as get/put/putIfAbsent.



回答3:


Unless you are talking about over 100,000 updates/reads per second I wouldn't consider using multiple threads. The reason is that thread-safe components take many times longer than components which are not. So if a component take 5x longer to be thread safe, you need to be using over 5 threads concurrently to break even, never mind go faster.

Multiple threads are much more useful when you have relatively expensive operations to perform. Updating a position or price is much more efficient as one thread.



来源:https://stackoverflow.com/questions/4556593/use-of-concurrenthashmap-eliminates-data-visibility-troubles

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