When i do a Collections.synchronizedMap(someHashMap), are all access to the map synchronized? Or only write operations (put) synchronized? How about if two threads are reading from the Map? Will it be synchronized? DOesnt seem necessary How abotu if one thread is doing put() and another is doing get()?

- 349,597
- 67
- 533
- 578

- 16,609
- 71
- 229
- 409
-
Because `Collections.synchronizedMap` is so basic it's almost unusable. There is the `ConcurrentHashMap` for more serious concurrent usage. – Boris the Spider Aug 14 '13 at 20:18
4 Answers
Look at the source code of SynchronizedMap
that's wrapping your Map
.
...
public V get(Object key) {
synchronized (mutex) {return m.get(key);}
}
public V put(K key, V value) {
synchronized (mutex) {return m.put(key, value);}
}
public V remove(Object key) {
synchronized (mutex) {return m.remove(key);}
}
... // more methods synchronized in the same way
From
public static <K,V> Map<K,V> synchronizedMap(Map<K,V> m) {
return new SynchronizedMap<>(m);
}
So, yes, all accesses are synchronized.

- 274,122
- 60
- 696
- 724
-
But unfortunately the reads and writes synchronize on an internal mutex, which makes it impossible for external code to iterate over the entires while holding the lock. EDIT: Sotirios and Affe are correct, and my comment should be disregarded. – dnault Aug 14 '13 at 20:20
-
1That's what the javadoc says: `It is imperative that the user manually synchronize on the returned map when iterating over any of its collection views:...` – Sotirios Delimanolis Aug 14 '13 at 20:21
-
2the mutex is indeed just 'this', The way it is written is simply idiomatic. Synchronizing the map to iterate it works properly. – Affe Aug 14 '13 at 20:22
-
The reason the code is synchronized on a `mutex` instead of directly on `this` is because the code is shared with `SynchronizedSortedMap` and needs to support returning a subMap that synchronizes on the parent map. See `Collections.SynchronizedSortedMap.subMap`. – Trevor Freeman Aug 14 '13 at 20:35
-
1@SotiriosDelimanolis I am aware, I am merely stating why the methods are not written as `public synchronized someMethod...`. It is not merely idiomatic it is done in order to provide support for returning a SynchronizedMap that is synchronizing on a parent map via the second constructor of SynchronizedMap. – Trevor Freeman Aug 14 '13 at 20:38
-
@increment1 Misunderstood your comment. Meant synchronized on the methods. – Sotirios Delimanolis Aug 14 '13 at 20:39
-
@SotiriosDelimanolis No worries, I was actually responding to Affe's comment (about the use of the mutex being idiomatic), and I should have addressed my comment appropriately. – Trevor Freeman Aug 14 '13 at 20:42
Yes, it synchronizes all operations. It doesn't use a multi-reader, single-writer approach - it's just as simple as synchronizing all access through a single monitor.

- 1,421,763
- 867
- 9,128
- 9,194
Both reads and writes are synchronised, which is necessary to ensure visibility.

- 321,522
- 82
- 660
- 783
All method calls on the collection are synchronized. Only one thread will be allowed to read/modify the collection at a time.
The synchronized* methods from Collections are not designed to be the best thread safe version/implementations. They are just suppose to be convenient.
Synchronization is a difficult problem and usually requires different synchronization approaches based on your specific scenario. If you require other types of thread-safety, there are lots of other thread safe collections available. You can also write the synchronization logic yourself.

- 5,641
- 1
- 23
- 35