中Java Concurrency In Practice
,给出下面的例子来说明如何创建不可变类:
http://www.javaconcurrencyinpractice.com/listings/ThreeStooges.java
此类具有:private final Set<String> stooges = new HashSet<String>();
在其构造函数中初始化:
public ThreeStooges() {
stooges.add("Moe");
stooges.add("Larry");
stooges.add("Curly");
}
并且有方法
public boolean isStooge(String name) {
return stooges.contains(name);
}
看看一个名字是否是三个傀儡之一。
但是当我这样做时:ThreeStooges ts = new ThreeStooges()
是否保证对象stooges
在其引用设置为之前将被正确构造(即正确初始化的状态)ts
?
换句话说,如果我发布了这个对象,是否有可能某些线程将其视为未正确初始化(即stooges
通过 访问时它会视为空isStooge()
)?
我的理解是,不可变对象在发布时将被正确构造并正确可见-(因为它使用最终实例变量)。我的理解正确吗?如果是,这个类仍然是不可变的吗?
编辑:从我看到的评论看来,很难相信一个对象可以在它的构造函数完成之前被其他线程看到。这是一个链接:http: //jeremymanson.blogspot.in/2008/05/double-checked-locking.html