JUC 进阶成神系列08—共享模型之无锁

CAS 与 volatile

volatile
获取共享变量时,为了保证该变量的可见性,需要使用 volatile 修饰。它可以用来修饰成员和静态成员变量,可以避免线程从自己的工作缓存中查找变量的值,必须到主存中获取它的值。线程保证 volatile 变量都是直接操作主存,即一个线程对volatile 变量的修改,对另一个线程可见。仅保证可见性,不能解决指令交错问题(原子性)。CAS 必须借助 volatile 才能读取到共享变量的最新值(源码中的 value 是用 volatile 修饰)来实现比较并交换的效果。

为什么无锁效率高?
无锁情况下,即使重试失败,线程始终在高速运行没有停歇,而 synchronized 会让线程在没有获得锁的时候,发生上下文切换进入阻塞。
但无锁情况下,因为线程要保持运行,需要额外 CPU 的支持。如果没有,虽然不会进入阻塞,但由于没有分到时间片,仍然会进入可运行状态,还会导致上下文切换,因此 CAS 需要多核 CPU 才能发挥优势,才能不发生上下文切换。线程数小于 CPU 核心数的情况是合适的。

CAS 的特点(结合 CAS 和 volatile 可以实现无锁并发,适用于线程数少,多核 CPU 的场景)
CAS 是基于乐观锁的思想:最乐观的估计,不怕别的线程来修改共享变量,就算改了也没关系,再重试。
synchronized 是基于悲观锁的思想,最悲观的估计,防着其他线程来修改共享变量。
CAS 体现的是无锁并发,无阻塞并发。因为没有使用 synchronized,所以线程不会陷入阻塞,这是效率提升的因素之一。但如果竞争激烈,重试频繁发生,效率反而会受影响。

原子整数

J.U.C 并发包提供了:AtomicBoolean、Atomicinteger、AtomicLong (分别是对布尔、整型、长整型进行封装,使其操作是原子的)。以 AtomicInteger 为例。在这里插入图片描述

原子引用

需要保护的数据并不一定都是基本类型的,因此需要原子引用类型:AtomicReference、AtomicMarkableReference、AtomicStampReference。

安全实现—使用 CAS在这里插入图片描述
在这里插入图片描述
ABA 问题及解决
ABA 问题:将 A 修改成 C。过程中将 A 改成 B,再将 B 改成 A,再将 A 改成 C。compareAndSet 是判断不出来中间 A 被修改过的,仅能判断出共享变量的值与最初值 A 是否相同。如果主线程希望只要有其他线程改动了共享变量,就算 CAS 失败,仅比较值不够,需要再加一个版本号
AtomicStampedReference (时间戳,理解成版本号)在这里插入图片描述
AtomicMarkableReference (布尔值,不关心版本号即引用变量更改了几次,只单词关心是否更该过) 在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

原子数组

需要修改的不是引用本身,而且引用或者对象里面的内容:AtomicIntegerArray、AtomicLongArray、AtomicReferenceArray (要保护的数组类型分别是整型、长整型、引用类型)。在这里插入图片描述
在这里插入图片描述

字段更新器

AtomicReferenceFieldUpdater、AtomicIntegerFieldUpdater、AtomicLongerFieldUpdater。利用字段更新器,可以针对对象的某个域 (Field) 进行原子操作,只能配合 volatile 修饰的字段使用,否则会出现异常。
在这里插入图片描述
在这里插入图片描述

原子累加器

对数字整数做累加操作,在 JDK 8 以后增加了专门做累加的类。

累加器性能比较
在这里插入图片描述
在这里插入图片描述
比较 AtomicLong 与 LongAdder。性能提升的原因很简单,就是在有竞争时,设置多个累加单元。Thread-0 累加 Cell[0],而 Thread-1 累加 Cell[1]…最后将结果汇总。这些它们在累加时操作不同的 Cell 变量,因此减少将 CAS 重试失败,从而提高性能。在这里插入图片描述

LongAdder源码
LongAdder 类有几个关键域在这里插入图片描述
cas 锁 -cellsBusy 如何实现e

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值