所以如果一个程序这样做:
static ArrayList<X> a = null;
static{
for(;;){X x = new X(); a.add(x)}
}
在共享列表上,静态初始化之后调用的唯一操作是 get() 和 xt()
X x = a.get(i); x.t();
并且 X 无权访问容器并且是线程安全的,这应该意味着像这样使用 Arraylist,没有同步是线程安全的,对吗?
所以如果一个程序这样做:
static ArrayList<X> a = null;
static{
for(;;){X x = new X(); a.add(x)}
}
在共享列表上,静态初始化之后调用的唯一操作是 get() 和 xt()
X x = a.get(i); x.t();
并且 X 无权访问容器并且是线程安全的,这应该意味着像这样使用 Arraylist,没有同步是线程安全的,对吗?
如果没有任何修改ArrayList
,那么您就没有理由担心它的线程安全性。
默认情况下,该静态块是线程安全的,因为它仅在加载类时运行一次(用于初始化)。
如果打算在创建列表后不对其进行修改,则强制执行:ArrayList
将Collections.unmodifiableList()
.
更好的是,如果您有 Guava 可用,请使用ImmutableList
.
线程安全只是可写对象的问题。初始化后,您的 ArrayList 是不可变的 - 因此是线程安全的。考虑在你的数组列表周围使用不可修改的包装器——它会
为了完整起见,请注意这样一个事实,虽然对 ArrayList 的操作是线程安全的,但对元素的操作不是。
Vector 是您想要的同步集合。
仅仅因为 Collection 的元素是线程安全的,并不能保证容器本身是线程安全的。基于我对并发的理解。
如果t
修改了支持集合,则它不是线程安全的。例如t
定义如下:
this.list.remove(this.x);
这将是不安全的。