CAS、volatile是JUC包实现同步的基础。Synchronized下的偏向锁、轻量级锁的获取、释放,lock机制下锁的获取、释放,获取失败后线程的入队等操作都是CAS操作锁标志位、state、队列完成的。

CAS过程

CAS的全称是Compare And Swap 即比较交换 ,是系统原语,由一系列系统的指令组成,不可被分割,简单的说就是CAS操作时一个原子性的操作。在sun.misc.unsafe类中,所有方法都是native的,都直接调用操作系统底层资源执行相应任务,比如直接操作内存,Java中CAS操作的执行依赖于Unsafe类的方法。其算法核心思想如下

其包含3个参数

  • V表示要更新的变量(即内存中的某变量的当前值)

  • E表示预期值

  • N表示新值

CAS操作需要我们提供一个期望值E,当 E == V 时,说明还没线程修改该值,当前线程可以进行修改为N,但如果期望值与当前线程不符,则说明该值已被其他线程修改,此时不执行更新操作,但可以选择重新读取该变量再尝试再次修改该变量 (也叫自旋) ,也可以放弃操作。

CAS的ABA问题

虽然CAS可以用很小的开销完成某些需要同步的操作,但也存在一些问题,比如ABA问题,并发量大的情况下自旋消耗过大的问题。关于ABA问题,举例说明:

我买东西付款100元后,由于一些原因,发起了两个付款线程 1、2。线程1 预期我的账户内存中的值为A元钱,要把它-100修改为B元。

这时线程1阻塞了,线程2顺利执行把A改为B。(正常情况下,线程1应该是CAS失败的,因为内存值B以经不等于它的预期值A了)

线程1还没来得及继续执行,你给我转账100元,并且这个转账 线程3 顺利执行完毕,我的账户+100,又变成A元。

在转账线程3完成后,线程1终于又开始执行了,它发现内存值还是A,于是它会执行扣款操作。我平白无故损失100元。

简单的说,ABA问题是: 两个进行同样操作的线程,本来是应该只能有一个操作成功,但是由与第三者介入二者之间修改数据,迷惑了二者中后执行的线程,使两个线程同样的操作都执行成功了。  比如扣了两次款!

解决办法是给我的余额值加个版本号,经过一次修改就更新一次版本。对于有些情况, 预期中的值、版本号 == 内存中值、版本号, 即二者都想等,才执行更新操作。

CAS及其ABA问题的更多相关文章

  1. 沉淀再出发:java中的CAS和ABA问题整理

    沉淀再出发:java中的CAS和ABA问题整理 一.前言 在多并发程序设计之中,我们不得不面对并发.互斥.竞争.死锁.资源抢占等等问题,归根到底就是读写的问题,有了读写才有了增删改查,才有了所有的一切 ...

  2. java并发编程(十三)----(JUC原子类)引用类型介绍(CAS和ABA的介绍)

    这一节我们将探讨引用类型原子类:AtomicReference, AtomicStampedRerence, AtomicMarkableReference.AtomicReference的使用非常简 ...

  3. Java高性能编程之CAS与ABA及解决方法

    Java高性能编程之CAS与ABA及解决方法 前言 如果喜欢暗色调的界面或者想换换界面,可以看看我在个人博客发布的 Java高性能编程之CAS与ABA及解决方法. CAS概念 CAS,全称Compar ...

  4. CAS的ABA问题详解

    CAS的ABA问题详解 ABA问题 在多线程场景下CAS会出现ABA问题,关于ABA问题这里简单科普下,例如有2个线程同时对同一个值(初始值为A)进行CAS操作,这三个线程如下 1.线程1,期望值为A ...

  5. CAS 和 ABA 问题

    CAS简介 CAS 全称是 compare and swap,是一种用于在多线程环境下实现同步功能的机制. CAS 它是一条CPU并发原语.操作包含三个操作数 -- 内存位置.预期数值和新值.CAS ...

  6. Java并发编程入门与高并发面试(三):线程安全性-原子性-CAS(CAS的ABA问题)

    摘要:本文介绍线程的安全性,原子性,java.lang.Number包下的类与CAS操作,synchronized锁,和原子性操作各方法间的对比. 线程安全性 线程安全? 线程安全性? 原子性 Ato ...

  7. Java CAS 和ABA问题

    独占锁:是一种悲观锁,synchronized就是一种独占锁,会导致其它所有需要锁的线程挂起,等待持有锁的线程释放锁. 乐观锁:每次不加锁,假设没有冲突去完成某项操作,如果因为冲突失败就重试,直到成功 ...

  8. 无锁编程(四) - CAS与ABA问题

    CAS 一般采用原子级的read-modify-write原语来实现Lock-Free算法,其中LL和SC是Lock-Free理论研究领域的理想原语,但实现这些原语需要CPU指令的支持,非常遗憾的是目 ...

  9. 谈论高并发(十二)分析java.util.concurrent.atomic.AtomicStampedReference看看如何解决源代码CAS的ABA问题

    于谈论高并发(十一)几个自旋锁的实现(五岁以下儿童)中使用了java.util.concurrent.atomic.AtomicStampedReference原子变量指向工作队列的队尾,为何使用At ...

随机推荐

  1. HTTP_1_Web及网络基础

    Web使用一种HTTP(HyperText TransFer Protocol,超文本协议)的协议作为规范,完成从客户端到服务器等一系列运作流程.可见web是建立在HTTP协议上通信的. 通常我们使用 ...

  2. context创建过程解析(一)之deployDescriptors

    总结:主要是创建Context对象,并且将默认context配置,host级别配置,context配置的值设置进去,设置docBase,如果是war包就解压到webapp的目录中,重新设置docBas ...

  3. T-SQL 镜像测试

    --====================================================== ----镜像计划建立 2016-05-10 17:05:16.463 hubiyun ...

  4. MySql性能优化读书比较<一> 数据类型

    一,选择优化的数据类型 1.更小的通常更好. 更小的数据类型通常占用更少的磁盘,内存和cpu缓存,通常更快. 2.简单就好 简单的数据类型操作,通常需要更少的CPU周期. 3.尽量避免NULL值 列可 ...

  5. go 学习之路(二)

    一.文件名 关键字 标识符 所有go源码都以.go结尾 标识符以字母或下划线开头,大小写敏感 a.boy b.Boy c.a+b d.0boy e._boy f.=_boy g._ 以上变量c.d.f ...

  6. Android平台使用Ceres Solver

    在Android平台上使用Ceres求解器,官方教程不明确,且编译过程遇到了很多问题. 环境 Ubuntu 18.04 源代码 https://github.com/Great-Keith/ceres ...

  7. 几大排序算法的Java实现(原创)

    几大排序算法的Java实现 更新中... 注: 该类中附有随机生成[min, max)范围不重复整数的方法,如果各位看官对此方法有什么更好的建议,欢迎提出交流. 各个算法的思路都写在该类的注释中了,同 ...

  8. ccf 201903-5 317号子任务(60分)

    看到这题,第一印象,用dijkstra算法求n次单源最短路,时间复杂度O(n^3),超时30分妥妥的. 于是用优先队列优化,O(n*mlogm),快很多,但依然30. 那么不妨换一种思路,题目要求的是 ...

  9. Assign the task HDU - 3974 (dfs序 + 线段树)

    有一家公司有N个员工(从1到N),公司里每个员工都有一个直接的老板(除了整个公司的领导).如果你是某人的直接老板,那个人就是你的下属,他的所有下属也都是你的下属.如果你是没有人的老板,那么你就没有下属 ...

  10. Redis——基础使用

    Redis总体介绍: Redis特性 Redis(REmote DIctionary Server),是一个开源的内存数据库 持久化:RDB.AOF 主备复制 丰富的数据结构 Lua脚本.事务 Red ...