java并發(fā)JUC工具包AtomicInteger原子整型語(yǔ)法基礎(chǔ)
AtomicInteger 類底層存儲(chǔ)一個(gè)int值,并提供方法對(duì)該int值進(jìn)行原子操作。AtomicInteger 作為java.util.concurrent.atomic
包的一部分,從Java 1.5開始引入。
1. AtomicInteger基礎(chǔ)用法
通過(guò)下文的AtomicInteger
構(gòu)造方法,可以創(chuàng)建一個(gè)AtomicInteger
對(duì)象,該對(duì)象的初始值默認(rèn)為0。AtomicInteger
提供get和set方法,獲取底層int整數(shù)值,與設(shè)置int整數(shù)值
//初始值為0的atomicInteger對(duì)象 AtomicInteger atomicInteger = new AtomicInteger(); //初始值為200的atomicInteger對(duì)象 AtomicInteger atomicInteger = new AtomicInteger(200); int currentValue = atomicInteger.get(); //100 atomicInteger.set(2453); //現(xiàn)在的值是 2453
但是上面的方法,對(duì)于AtomicInteger
而言并不是它的核心內(nèi)容,AtomicInteger
核心內(nèi)容體現(xiàn)在它的原子性,我們下文介紹。
2. 什么時(shí)候需要使用AtomicInteger
我們通常在以下的兩種場(chǎng)景下使用AtomicInteger
多線程并發(fā)場(chǎng)景下操作一個(gè)計(jì)數(shù)器,需要保證計(jì)數(shù)器操作的原子性。
進(jìn)行數(shù)值比較,如果給定值與當(dāng)前值相等,進(jìn)行數(shù)值的更新操作,并實(shí)現(xiàn)操作的非阻塞算法。
2.1. 原子計(jì)數(shù)器場(chǎng)景
把AtomicInteger
作為一個(gè)計(jì)數(shù)器使用,AtomicInteger
提供了若干方法進(jìn)行加法、減法的原子操作。
比如從一個(gè)map里面獲取值,用get()方法,這是第一個(gè)操作;獲取到值之后給這個(gè)值加上n,這是第二個(gè)操作;將進(jìn)行過(guò)加法運(yùn)算的值,再次放入map里面是第三個(gè)操作。所謂操作的原子性是指:在多線程并發(fā)的場(chǎng)景下,上面的三個(gè)操作是原子性的,也就是不可分割的。不會(huì)出現(xiàn)A線程get了數(shù)值,B線程同時(shí)也get到了該數(shù)值,兩個(gè)線程同時(shí)為該值做運(yùn)算并先后再次放入的情況,這種情況對(duì)于AtomicInteger
而言是不會(huì)出現(xiàn)的,AtomicInteger
操作是線程安全的、不可分割的。
addAndGet()
- 將給定的值加到當(dāng)前值上,并在加法后返回新值,并保證操作的原子性。
getAndAdd()
- 將給定的值加到當(dāng)前值上,并返回舊值,并保證操作的原子性。
incrementAndGet()
- 將當(dāng)前值增加1,并在增加后返回新值。它相當(dāng)于++i
操作,并保證操作的原子性。
getAndIncrement()
- 將當(dāng)前值增加1并返回舊值。相當(dāng)于++i
操作,并保證操作的原子性。
decrementAndGet()
- 將當(dāng)前值減去1,并在減去后返回新值,相當(dāng)于i--
操作,并保證操作的原子性。
getAndDecrement()
- 將當(dāng)前值減去1,并返回舊值。它相當(dāng)于 --i
操作,并保證操作的原子性。
下面是AtomicInteger原子性操作方法的例子
public class Main { public static void main(String[] args) { //初始值為100的atomic Integer AtomicInteger atomicInteger = new AtomicInteger(100); System.out.println(atomicInteger.addAndGet(2)); //加2并返回102 System.out.println(atomicInteger); //102 System.out.println(atomicInteger.getAndAdd(2)); //先獲取102,再加2 System.out.println(atomicInteger); //104 System.out.println(atomicInteger.incrementAndGet()); //加1再獲取105 System.out.println(atomicInteger); //105 System.out.println(atomicInteger.getAndIncrement()); //先獲取105再加1 System.out.println(atomicInteger); //106 System.out.println(atomicInteger.decrementAndGet()); //減1再獲取105 System.out.println(atomicInteger); //105 System.out.println(atomicInteger.getAndDecrement()); //先獲取105,再減1 System.out.println(atomicInteger); //104 } }
2.2. 數(shù)值比對(duì)及交換操作
compareAndSet操作將一個(gè)內(nèi)存位置的內(nèi)容與一個(gè)給定的值進(jìn)行比較,只有當(dāng)它們相同時(shí),才會(huì)將該內(nèi)存位置的內(nèi)容修改為一個(gè)給定的新值。這個(gè)過(guò)程是以單個(gè)原子操作的方式完成的。
compareAndSet方法:如果當(dāng)前值==預(yù)期值,則將值設(shè)置為給定的更新值。
boolean compareAndSet(int expect, int update)
expect
是預(yù)期值
update
是更新值
AtomicInteger compareAndSet() 方法的例子
import java.util.concurrent.atomic.AtomicInteger; public class Main { public static void main(String[] args) { //初始值為100的atomic Integer AtomicInteger atomicInteger = new AtomicInteger(100); //當(dāng)前值100 = 預(yù)期值100,所以設(shè)置atomicInteger=110 boolean isSuccess = atomicInteger.compareAndSet(100,110); System.out.println(isSuccess); //輸出結(jié)果為true表示操作成功 //當(dāng)前值110 = 預(yù)期值100?不相等,所以atomicInteger仍然等于110 isSuccess = atomicInteger.compareAndSet(100,120); System.out.println(isSuccess); //輸出結(jié)果為false表示操作失敗 } }
3. 總結(jié)
AtomicInteger
可以幫助我們?cè)诓皇褂胹ynchronized同步鎖的情況下,實(shí)現(xiàn)在多線程場(chǎng)景下int數(shù)值操作的線程安全,操作的原子性。并且使用AtomicInteger
來(lái)實(shí)現(xiàn)int數(shù)值的原子操作,遠(yuǎn)比使用synchronized同步鎖效率更高。
java.util.concurrent.atomic
包不僅為我們提供了AtomicInteger
,還提供了AtomicBoolean布爾原子操作類、AtomicLong長(zhǎng)整型布爾原子操作類、AtomicReference對(duì)象原子操作類、AtomicIntegerArray整型數(shù)組原子操作類、AtomicLongArray長(zhǎng)整型數(shù)組原子操作類、AtomicReferenceArray對(duì)象數(shù)組原子操作類。
以上就是java并發(fā)JUC工具包AtomicInteger原子整型語(yǔ)法基礎(chǔ)的詳細(xì)內(nèi)容,更多關(guān)于JUC AtomicInteger原子整型語(yǔ)法的資料請(qǐng)關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
Spring中HandlerMethod類源碼詳細(xì)解析
這篇文章主要介紹了Spring中HandlerMethod類源碼詳細(xì)解析,HandlerMethod類用于封裝控制器方法信息,包含類信息、方法Method對(duì)象、參數(shù)、注解等信息,具體的接口請(qǐng)求是可以根據(jù)封裝的信息調(diào)用具體的方法來(lái)執(zhí)行業(yè)務(wù)邏輯,需要的朋友可以參考下2023-11-11基于SpringBoot實(shí)現(xiàn)圖片上傳及圖片回顯
本篇文章主要介紹了SpringBoot如何實(shí)現(xiàn)圖片上傳及圖片回顯,文中通過(guò)實(shí)例代碼給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友參考下吧2022-08-08Java StackTraceElement實(shí)例代碼
這篇文章主要介紹了Java StackTraceElement實(shí)例代碼,分享了相關(guān)代碼示例,小編覺(jué)得還是挺不錯(cuò)的,具有一定借鑒價(jià)值,需要的朋友可以參考下2018-02-02