Reputation: 4280
I want to pass a pre-built Map to multiple threads that are going to only read the values from the Map simultaneously. Do I need to worry about concurrent access and use the ConcurrentHashMap instead of HashMap in this case?
Upvotes: 5
Views: 733
Reputation: 719596
You still need to make sure that there is a "happens-before" relationship between the thread that creates and initializes the Map, and the threads that subsequently read it. If there is no such relationship, it is theoretically possible for the reading threads to see stale data.
If you create and populate the Map in the thread that starts the other threads ... before it does this ... you should be fine.
Another simple way to ensure safety is to do something like this:
public class Foo {
private final Map map;
public Foo(....) {
map = new HashMap();
// populate
}
public Map getMap() {
// If the 'map' is final, and nothing changes it apart from
// the constructor, this method doesn't need to be synchronized.
}
Both of these will result in a "happens-before" relationship between the creation / initialization, and each thread's first use of the Map.
You could also declare map
in the above to be volatile
, but is likely to cause more cache flushes than strictly need to occur; i.e. you'll take a small performance hit.
Upvotes: 7
Reputation: 200296
You always need to worry about thread safety. In your specific example, it will be enough if you
volatile
variable to refer to it.Or, if that is an option, make sure the threads are not started until the map is ready.
Upvotes: 3
Reputation: 23913
What you could do, additionally, in order to ensure that will be handled just for reading operations is to give back an Collections.unmodifiableMap(Map).
Upvotes: 3
Reputation: 1352
No you dont need to use it. Conflicts are generated only in following cases:
When each thread is only trying to read the values, no conflicts are generated.
Upvotes: 1
Reputation: 62772
It is safe to pass the HashMap if all the threads are reading it. However, before passing the map I would call Collections.unmodifiableMap() to make sure that if one of thread accidentally modified it because some programmer in the future did not respect the current contract you will get an exception.
Upvotes: 2
Reputation: 22720
No, You dont have to worry about it.
Unless until someone going to change pre-built map while thread are accessing it.
Upvotes: 1
Reputation: 13925
In theory, concurrent reading should not cause problems on collections.
However if you modify it even once, it is prone to error, and then you should use a concurrent version.
Upvotes: 2