Java中的CAS机制

需要解决的问题

首先我们要知道CAS机制是要解决什么问题的。

当同时有多个线程来访问某个共享变量,并对该变量各自的操作,比如++操作,然后写回给这个变量。在不加限制的情况下,很可能发生的一种情况是:线程A和线程B同时读走了此时变量 p 的值(假设为100),各自++操作,然后拿着各自的 p (101)来写回。这个时候线程A先写回,内存中的 p 变成了101,然后线程B再写回,不管内存中的 p 的值是多少,直接写回为101。这就导致了数据丢失的问题。本来应该是102 的结果,现在丢失了一次—++操作。

CAS机制就是来解决这种问题的。

CAS机制的过程

CAS就是Compare and Swap,也就是比较并替换的意思。

CAS机制的过程是:

同样的,线程A和线程B读走了内存中的共享变量 p (100);然后A和B会记录读取变量时该变量的值,接着进行各自的++操作。最后线程A和线程B都带着 p (101)回来写回,假设A先写回,A需要先比对内存中 p 的值和自己读取时记录的值是否相等,只有相等的情况下才会写入内存。这时内存中的变量 p 的值为101,然后B再写回,也会进行比对,发现 p 的值为101,和自己记录的100不相等,那么这次写入就是失败的,这次数据也就不会再去写入。然后线程B需要重新执行一遍读取,++操作,对比的操作,直到写入时内存中的值和读取时内存中的值相同,才会完成写入。

ABA问题

ABA问题是潜藏在CAS机制中的。

同样假设线程A和线程B访问共享变量 p (100),A执行了一次++操作,然后写回内存,这时内存中 p 的值为101。B由于某些原因还没有写回,线程C读取 p ,并执行了一次 - - 操作,然后写入,此时内存中的变量 p 的值为100,与A、B读取时时相同。这时B再写入,发现内存中 p 的值为100,和自己记录的值是相同的,就会直接写入。但这个流程是不对的,变量 p 的值是发生过改变的。

为了解决这个问题我们可以给每个数据加一个版本号。

比如上面说到的变量 p :100 → 101 → 100 → 101就可以变成:

p :100(01)→ 101(01) → 100(02)这时候线程B再来写回就会发现版本号不对,写入失败,重新读取。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值