volatile三特性学习笔记

三大特性

jmm编程的三大特性
1:可见性
2:原子性
3:有序性
但是volatile对于三大特性却只支持两个(可见性和禁止指令重排),它不不保证原子性

可见性

这个是可见性的理论,以及正常java程序的内存流程,可见性会将修改去及时的通知主内存,让其他的线程也看到

场景:现在有个对象,里面有个成员变量,主线程中开了一个新的线程,新线程和主线程操作同一个对象,但是对象里面值进行改变时,另一个对象是不知道的。将成员变量加上volatile则当某一线程将主内存值改变时,所有线程立刻就会被感知
可见性理论逻辑

这个是可见性的理论,以及正常java的内存流程,可见性会将修改及时通知主内存,让其他的线程也看到

volatile不保证原子性

假如当成千上万个线程操作成员变量时,因为没原子性,可能读到相同的值后进行不同运算进行写入,但是后面写入就会覆盖原来的。就是因为在其他线程未运算结束时,某线程又拿到原值进行运算以及写入就会导致其他线程的值被覆盖

解决不保证原子性问题
1.可以用synchronized关键字,但是不必要。这个方案不建议。
2.可以用java.util.concurrent下的AtomicInteger,因为它具有原子性(java.util.concurrent里面是个提供原子性的类,其中有AtomicInteger,原子性的integer值。)

禁止指令重排

系统为了代码的性能可能会对指令顺序进行重新排序。也就是说不见得会按照源代码中的编写顺序去执行顺序。所以这就是指令重
指令重排

在这里插入图片描述

下面是指令重排的小结

在这里插入图片描述

在这里插入图片描述

单例模式的DCl不一定安全(因为指令重排)。看下

在这里插入图片描述

上面图片这种高并发情况下,很低几率仍然会出现问题,并不是绝对安全的单例。具体原因看下面

在这里插入图片描述
在这里插入图片描述

最后的解决方案,将对象变量加上volatile修饰,禁止指令重排
在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值