understanding java's synchronized collections

偶尔善良 提交于 2019-12-08 02:37:46

问题


I'm reading the java official doc regarding wrappers implementation, which are static methods in Collections used to get synchronized collection, for example : List<Type> list = Collections.synchronizedList(new ArrayList<Type>()); ...
the thing that I did not understand is the following (I quote from the java doc ) :

A collection created in this fashion is every bit as thread-safe as a normally synchronized collection, such as a Vector. In the face of concurrent access, it is imperative that the user manually synchronize on the returned collection when iterating over it. The reason is that iteration is accomplished via multiple calls into the collection, which must be composed into a single atomic operation...

how it could be every bit as thread-safe an need to manually synchronize when iterating ??


回答1:


It is thread safe in the sense that each of it's individual methods are thread safe, but if you perform compound actions on the collection, then your code is at risk of concurrency issues.

ex:

List<String> synchronizedList = Collections.synchronizedList(someList);
synchronizedList.add(whatever); // this is thread safe

the individual method add() is thread safe but if i perform the following:

List<String> synchronizedList = Collections.synchronizedList(someList);
if(!synchronizedList.contains(whatever))
       synchronizedList.add(whatever); // this is not thread safe

the if-then-add operation is not thread safe because some other thread might have added whatever to the list after contains() check.




回答2:


There is no contradiction here: collections returned from synchronizedXyz suffer the same shortcoming as synchronized collections available to you directly, namely the need to manually synchronize on iterating the collection.

The problem of external iteration cannot be solved by a better class design, because iterating a collection inherently requires making multiple calls to its methods (see this Q&A for detailed explanation).

Note that starting with Java 1.8 you can iterate without additional synchronization using forEach method of your synchronized collection*. This is thread-safe, and comes with additional benefits; see this Q&A for details.

The reason this is different from iterating externally is that forEach implementation inside the collection takes care of synchronizing the iteration for you.



来源:https://stackoverflow.com/questions/49489854/understanding-javas-synchronized-collections

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