java 为什么静态内部类单例线程是安全的
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/17799976/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
why is static inner class singleton thread safe
提问by huashui
As the title said, why is static nested class singleton thread-safe?
正如标题所说,为什么静态嵌套类单例线程安全?
public class Singleton {
private static class SingletonHolder {
public static Singleton instance;
public static Singleton getInstance() {
if (null == instance) {
instance = new Singleton();
}
}
}
public static Singleton getInstance() {
return SingletonHolder.getInstance();
}
}
回答by Tom Hawtin - tackline
The code you show is not technically thread-safe. This sort of dodgy code often gets mangles.
您显示的代码在技术上不是线程安全的。这种狡猾的代码经常被破坏。
The code should look like:
代码应如下所示:
public class Singleton {
private static class SingletonHolder {
public static final Singleton instance = new Singleton();
}
public static Singleton getInstance() {
return SingletonHolder.instance;
}
}
Here we are assigning within a static initialiser (of SingletonHolder
), which will be seen by any thread accessing it with correct happens-beforerelationship. There's nothing really special about the nested class, it just allows the outer class to be used without immediately constructing the singleton object. Almost certainly this is entirely pointless, but it seems to please some people.
在这里,我们在静态初始化器 (of SingletonHolder
) 中进行分配,任何以正确的发生之前关系访问它的线程都可以看到它。嵌套类并没有什么特别之处,它只是允许使用外部类而无需立即构造单例对象。几乎可以肯定这完全没有意义,但它似乎取悦了一些人。
As ever [mutable] singletons are a really badidea.
一如既往[可变]单身是一个非常糟糕的主意。
回答by DaoWen
It's thread-safe because the JVM handles lazily loading the nested class.
它是线程安全的,因为 JVM 处理延迟加载嵌套类。
However, the code you posted doesn't seem to be using this pattern correctly (you shouldn't have a null check), and I think that actually breaks the thread safety. Here's a nice article where you can read more about why this pattern works and how to use it correctly:
但是,您发布的代码似乎没有正确使用此模式(您不应该进行空检查),我认为这实际上破坏了线程安全。这是一篇不错的文章,您可以在其中阅读有关此模式为何起作用以及如何正确使用它的更多信息: