重要网址
https://blog.csdn.net/wufaliang003/article/details/78797203 ABA问题详细介绍
一、什么是CAS操作
cas全称是compare and swap 比较交换 传入三个参数,旧的值、期待的值、想替换的值。会获得变量的之前的值,与期待的值相比,如果相同替换值给变量,如果不同返回false。
cas是unsafe类下的native方法,使用c++进行实现,主要是直接操作cpu指令进行原子性操作。
cas使用于低并发的场景。
二、CAS和synchronized适用场景
1、对于资源竞争较少的情况,使用synchronized同步锁进行线程阻塞和唤醒切换以及用户态内核态间的切换操作额外浪费消耗cpu资源;
而CAS基于硬件实现,不需要进入内核,不需要切换线程,操作自旋几率较少,因此可以获得更高的性能。
2、对于资源竞争严重的情况,CAS自旋的概率会比较大,从而浪费更多的CPU资源,效率低于synchronized。
使用CAS在线程冲突严重时,会大幅降低程序性能;CAS只适合于线程冲突较少的情况使用。而synchronized在jdk1.6之后,已经改进优化。synchronized的底层实现主要依靠Lock-Free的队列,基本思路是自旋后阻塞,竞争切换后继续竞争锁,稍微牺牲了公平性,但获得了高吞吐量。在线程冲突较少的情况下,可以获得和CAS类似的性能;而线程冲突严重的情况下,性能远高于CAS。
三、CAS的问题
1. CAS仅仅只能针对于一个变量进行修改,可以封装成对象适用atomicRefence进行使用。
2. CAS具有ABA问题。
3. CAS只适合于线程冲突较少的情况使用。
四、ABA问题
atomicWarkingRefence类可以进行版本验证。
ABA问题导致的原因,是CAS过程中只简单进行了“值”的校验,再有些情况下,“值”相同不会引入错误的业务逻辑(例如库存),有些情况下,“值”虽然相同,却已经不是原来的数据了。
优化方向:CAS不能只比对“值”,还必须确保的是原来的数据,才能修改成功。
常见实践:“版本号”的比对,一个数据一个版本,版本变化,即使值相同,也不应该修改成功。