双检锁(DCL)的分析
public class Singleton
{
private static volatile Singleton instance;
private Singleton() {}
public static Singleton getInstance()
{
if(instance==null)
{
synchronized(Singleton.class)
{
if(instance==null)
{
instance = new Singleton();
}
}
}
return instance;
}
}
1、第二个if(instance==null)判断的原因:
- 首个线程在进入同步块创建对象的过程中,可能有其他线程通过第一个判断试图进入同步块,此时会被阻塞在同步块队列中;
- 当首个线程创建完毕后,同步块阻塞队列中的线程会进入同步块,此时
instance!=null,防止了对象再创建
2、volatile作用:
在对象创建阶段,对象创建不是原子操作,可以分为:
-
在堆中分配对象内存空间
-
执行构造方法,初始化对象
-
将引用instance指向这个对象的堆内地址
此时2、3步可能发生重排,使instance指向一个未创建完成的对象;此时若有线程要获取instance,则会获取到这个还未创建完成的对象,发生错误

浙公网安备 33010602011771号