在java中,大家都会接触到指令重排序这个概念,在创建懒汉单例模式的时候都知道要加个volatile,可以解决重排序问题,但是刚开始我却发现很难理解指令重排序,不知道创建单例模式如果重排序会有什么问题,不知道该什么时候需要用volatile防止重排序。直到今天算是又进一步理解了,所以赶紧做了笔记,画了图分享给大家看看。
单例模式中如果不加volatile有可能出现指令重排序,比如:
private static ObjInstance instance;
//线程1
if(instance!=null){
instance.method();
}
//线程2
if(instance==null){
synchronized (ObjInstance.class){
if(instance==null){
instance = new ObjInstance();
}
}
}
//其中instance = new ObjInstance();分为3步骤:
(1)____给对象分配一块内存空间
(2)__new ObjInstance()__初始化对象
(3)instance= __new ObjInstance()__instance指向刚分配的地址
//但是(2)和(3)可能重排序,变成
(1)____给对象分配一块内存空间
(2)instance= ____instance指向刚分配的地址
(3)__new ObjInstance()__初始化对象
//这时候就可能执行到2的时候,if(instance!=null)结果为真就继续执行下去了,所以要加volatile
下面是用图的方式,可能比较好理解。