奇瑞艾瑞泽7挂档杆的档头?java 单例模式中双重检查锁定 volatile 的作用

时间:2018-02-13 08:00:03   浏览:次   点击:次   作者:   来源:   立即下载

看手动自动了,自动档逆时针旋转即可,自手动挡需要将单位上边的盖拆掉就行

谢邀请,

非专业维修人员,无法给你解答,

谢谢邀请回答。万能的度娘会帮助你的

逆时针旋转就对了

钢锯

看题目描述,其实题主已经清楚了volatile的禁止指令重排序、保证内存可见性的作用。只是想知道在单例模式的双重检查锁定中volatile的作用而已。

个人观点是,两种作用都有:

volatile对singleton的创建过程的重要性:

禁止指令重排序(有序性)

实例化①个对象其实可以分为③个步骤:

  (①)分配内存空间。

  (②)初始化对象。

  (③)将内存空间的地址赋值给对应的引用。

但是由于操作系统可以对指令进行重排序,所以上面的过程也可能会变成如下过程:

  (①)分配内存空间。

  (②)将内存空间的地址赋值给对应的引用。

  (③)初始化对象

如果是这个流程,多线程环境下就可能将①个未初始化的对象引用暴露出来,从而导致不可预料的结果(如题目的描述,这里就是因为 instance = new Singleton(); 不是原子操作,编译器存在指令重排,从而存在线程① 创建实例后(初始化未完成),线程② 判断对象不为空后对其操作,但实际对象仍为空,造成错误)。因此,为了防止这个过程的重排序,我们需要将变量设置为volatile类型的变量,volatile的禁止重排序保证了操作的有序性。

Singleton对象的内存可见性

这里由于synchronized锁的是Singleton.class对象,而不是Singleton对象,所以synchronized只能保证Singleton.class对象的内存可见性,但并不能保证Singleton对象的内存可见性;这里用volatile声明Singleton,可以保证Singleton对象的内存可见性。这①点作用也是非常重要的(如题目的描述,避免因为线程① 创建实例后还只存在自己线程的工作内存,未更新到主存。线程 ② 判断对象为空,创建实例,从而存在多实例错误)。

收起

相关推荐

相关应用

平均评分 0人
  • 5星
  • 4星
  • 3星
  • 2星
  • 1星
用户评分:
发表评论

评论

  • 暂无评论信息