深入理解CAS
深入理解CAS
- 
什么是 CAS大厂你必须要深入研究底层!有所突破! public class Test01 { // CAS compareAndSet : 比较并交换! public static void main(String[] args) { AtomicInteger atomicInteger = new AtomicInteger(2021); // 期望、更新 // public final boolean compareAndSet(int expect, int update) // 如果我期望的值达到了,那么就更新,否则,就不更新, CAS 是CPU的并发原语! System.out.println(atomicInteger.compareAndSet(2021, 2022)); System.out.println(atomicInteger.get()); System.out.println(atomicInteger.compareAndSet(2021, 2022)); System.out.println(atomicInteger.get()); } }
- 
Unsafe 类  
 
CAS : 比较当前工作内存中的值和主内存中的值,如果这个值是期望的,那么则执行操作!如果不是就 一直循环!
缺点:
1、 循环会耗时
2、一次性只能保证一个共享变量的原子性
3、ABA问题
- 
CAS : ABA 问题(狸猫换太子)  public class Test01 { // CAS compareAndSet : 比较并交换! public static void main(String[] args) { AtomicInteger atomicInteger = new AtomicInteger(2021); // 期望、更新 // public final boolean compareAndSet(int expect, int update) // 如果我期望的值达到了,那么就更新,否则,就不更新, CAS 是CPU的并发原语! // ============== 捣乱的线程 ================== System.out.println(atomicInteger.compareAndSet(2021, 2022)); System.out.println(atomicInteger.get()); System.out.println(atomicInteger.compareAndSet(2022, 2021)); System.out.println(atomicInteger.get()); // ============== 期望的线程 ================== System.out.println(atomicInteger.compareAndSet(2021, 2022)); System.out.println(atomicInteger.get()); } }
解决方法:引入原子引用!
public class Test01 {
    // AtomicStampedReference 如果泛型是包装类,注意对象的引用问题
    // 正常业务引用的是对象
    public static void main(String[] args) {
        AtomicStampedReference<Integer> integerAtomicStampedReference = new AtomicStampedReference<>(11,1);
        new Thread(()->{
            int stamp = integerAtomicStampedReference.getStamp();//获取版本号
            System.out.println("版本号a1:"+stamp);
            try {
                TimeUnit.SECONDS.sleep(2);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            //版本号+1
            System.out.println(integerAtomicStampedReference.compareAndSet(11, 12,
                    integerAtomicStampedReference.getStamp(), integerAtomicStampedReference.getStamp() + 1));
            System.out.println("版本号a2:"+integerAtomicStampedReference.getStamp());
            //版本号+1
            System.out.println(integerAtomicStampedReference.compareAndSet(12, 11,
                    integerAtomicStampedReference.getStamp(), integerAtomicStampedReference.getStamp() + 1));
            System.out.println("版本号a3:"+integerAtomicStampedReference.getStamp());
        },"a").start();
        new Thread(()->{
            int stamp = integerAtomicStampedReference.getStamp();//获取版本号
            System.out.println("版本号b1:"+stamp);
            try {
                TimeUnit.SECONDS.sleep(2);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            //版本号+1
            System.out.println(integerAtomicStampedReference.compareAndSet(11, 22,
                    integerAtomicStampedReference.getStamp(), integerAtomicStampedReference.getStamp() + 1));
            System.out.println("版本号b2:"+integerAtomicStampedReference.getStamp());
        },"b").start();
    }
}
 
                    
                
 
                
            
         
         浙公网安备 33010602011771号
浙公网安备 33010602011771号