1. 程式人生 > 實用技巧 >多執行緒-CAS操作

多執行緒-CAS操作

CAS操作號稱無鎖優化,也叫作自旋;對於一些常見的操作需要加鎖,然後jdk就提供了一些以Atomic開頭的類,這些類內部自動帶了鎖,當然這裡的鎖並非是用synchronized來實現的,而是通過CAS操作來實現的;

一、下面是AtomicInteger 的使用:

package com.designmodal.design.juc01;

import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.atomic.AtomicInteger;

/**
 * @author D-L
 * @Classname T03_AtomicInteger
 * @Version 1.0
 * @Description  使用 AtomicInteger 類解決常見的 多執行緒count++
 *               其內部使用了CAS操作來保證原子性  但是不能保證多個方法連續呼叫都是原子性
 * @Date 2020/7/21 0:35
 
*/ public class T03_AtomicInteger { //使用AtomicInteger類 AtomicInteger count = new AtomicInteger(0); public void m(){ for (int i = 0; i < 10000; i++) { //等同於 在 count++ 上加鎖 count.incrementAndGet(); } } public static void main(String[] args) { T03_AtomicInteger t
= new T03_AtomicInteger(); List<Thread> threads = new ArrayList<>(); for (int i = 0; i < 10; i++) { threads.add(new Thread(t::m , "Thread" + i)); } threads.forEach((o) -> o.start()); threads.forEach(o ->{ try { o.join(); }
catch (InterruptedException e) { e.printStackTrace(); } }); System.out.println(t.count); } }

二、當然達到使用的級別很簡單,看一下API就好了,通過上面的小程式,下面主要來聊一聊原理:

1、首先小程式中定義了一個AtomicInteger 型別的變數count;

 AtomicInteger count = new AtomicInteger(0);
 public void add(){
count.incrementAndGet();
}

2、呼叫了AtomicInteger類中incrementAndGet();

/**
     * Atomically increments by one the current value.
     *
     * @return the updated value
     */
    public final int incrementAndGet() {
        return unsafe.getAndAddInt(this, valueOffset, 1) + 1;
    }

3、呼叫unsafe類中的getAndAddInt(Object var1, long var2, int var4)方法;

public native int getIntVolatile(Object var1, long var2);
public final native boolean compareAndSwapInt(Object var1, long var2, int var4, int var5);


 public final int getAndAddInt(Object var1, long var2, int var4) {
        int var5;
        do {
            var5 = this.getIntVolatile(var1, var2);
        } while(!this.compareAndSwapInt(var1, var2, var5, var5 + var4));

        return var5;
    }