CAS有点: 可以有效提升效率和保证原子性
CAS机制: 首先去查询原值,在要修改的时候拿着拿到的值和原值比较是不是一样,如果一样就修改, 不一样就重新获取一次原值循环流程
问题: 有几率发送该线程一直在循环获取值的场景,造成CPU大量开销和ABA问题, 只能保证一个共享变量的原子性,不过可以用AtomicReference来引用对象
ABA问题描述:
线程1获取到原值A, 线程2也获取到原值A, 这时线程2把A改成了B,然后线程3获取到了原值B,讲B改成了A,这时线程1再去修改值会发现依旧可以修改, 因为原值依旧是A,
看着没啥问题,对应一些修改数值之类确实也不会影响结果,但是如果是栈队列的话就有问题了, 现在有一个栈队列分别是A-B-C, 线程1拿到栈顶A要改为D,这时线程2拿到队列把A-B-C改成 A-C, 这时线程1去修改栈顶A改为B后栈变成了B-C
ABA问题解决: 更改值时写入版本号(版本号+1)或者时间戳,每次执行都要对比版本号,这样就不会发生ABA问题了
AtomicReference和AtomicStampedReference区别:
本质上是没有啥区别的, 不同点就是AtomicReference虽然保证了原子性但是会存在ABA的情况,AtomicStampedReference可以设置一个版本号来解决
compareAndSet方法, 如果1等于原值, 就改为2,否则不处理
getAndSet方法,获取原值进行比较,如果相等,赋值, 同时可以返回旧的原值