AtomicInteger詳解
**上一篇文章談到volatile不能保證原子性, 但如果業(yè)務(wù)需要原子性的時(shí)候, 需要用什么呢?**
- 使用synchronized, Lock 等加鎖機(jī)制進(jìn)行原子操作
- 使用原子操作類, java.util.concurrent.atomic下面的原子操作類進(jìn)行原子操作
下面我們主要分析一下原子操作類AtomicInteget
AtomicInteget
代碼演示
AtomicInteger b = new AtomicInteger();
@Test
public void testAtomicAdd() throws InterruptedException {
for (int i = 0; i < 100; i++) {
new Thread(() -> {
for (int j = 0; j < 1000; j++){
b.incrementAndGet();
}
}).start();
}
TimeUnit.SECONDS.sleep(1);
System.out.println("最后結(jié)果: " + b);
}

執(zhí)行結(jié)果.png

源碼分析.png
CAS 的缺點(diǎn)
- 循環(huán)時(shí)間開銷很大(如果很到線程進(jìn)行操作, 就會(huì)存在很多while循環(huán), 導(dǎo)致CUP開銷很大)
- 只能保證一個(gè)共享變量的原子操作
- 存在ABA問題

ABA問題分析.png
ABA問題解決
添加樂觀鎖機(jī)制, 增加一個(gè)版本號(hào), 使用AtomicStampedReference類

ABA問題解決.png
總結(jié)
volatile可以理解為輕量級(jí)的synchronized, 最適用一個(gè)線程寫,多個(gè)線程讀的場(chǎng)合.若需要保證一個(gè)共享變量的原子性, 使用java.util.concurrent.atomic包下的原子操作類, 使用時(shí)需注意ABA問題.