鍍金池/ 問答/Java  Linux/ Java :多核 CPU 多線程下,原子操作有先后順序嗎?

Java :多核 CPU 多線程下,原子操作有先后順序嗎?

譬如 JAVA 里 ConcurrentHashMap 的 putIfAbsent 方法

兩個線程同時調(diào)用這個方法 putIfAbsent ( key1,value1 )

他們之間會有先后順序嗎?不會兩個都成功吧?

回答
編輯回答
別瞎鬧

不要把原子操作和同步操作弄混了。

原子操作:其中的代碼的執(zhí)行具有完整性保證,要么全部成功,要么全部失敗,不會出現(xiàn)部分成功的情況

同步操作:同一時間僅有一個線程可以進入并執(zhí)行。同步的代碼自動具有原子性

所以,如果代碼只有原子性,但不是同步的,那么多個線程是可以同時執(zhí)行的,并且可能會有先后順序。

但如果代碼是同步的,那么同一時間不可能會有多個線程進入,即使是多核系統(tǒng)也是一樣。

putIfAbsent是同步的,所以多個線程同時調(diào)用的時候必然是一個一個執(zhí)行,key相同的情況下,僅第一個執(zhí)行的線程會成功。

2018年4月5日 11:33
編輯回答
局外人

個人還沒有研究這么深入,只找到相關(guān)討論,你可以看一下:
對于多核CPU java中Thread.currentThread() 指的是哪個核上的線程?
JAVA多線程里面CAS中比較和更新怎么保證同步?

在第二個討論中,有這么一段話:

但我們只需要對此共享變量的操作是原子就可以了,而總線鎖定把CPU和內(nèi)存的通信給鎖住了,使得在鎖定期間,其他處理器不能操作其他內(nèi)存地址的數(shù)據(jù),從而開銷較大,所以后來的CPU都提供了緩存一致性機制,Intel的奔騰486之后就提供了這種優(yōu)化。緩存一致性機制整體來說,是當(dāng)某塊CPU對緩存中的數(shù)據(jù)進行操作了之后,就通知其他CPU放棄儲存在它們內(nèi)部的緩存,或者從主內(nèi)存中重新讀取。

作者:潛龍勿用
鏈接:https://www.zhihu.com/questio...
來源:知乎
著作權(quán)歸作者所有。商業(yè)轉(zhuǎn)載請聯(lián)系作者獲得授權(quán),非商業(yè)轉(zhuǎn)載請注明出處。

所以 CPU 自身有 緩存一致性機制,JVM 層面再有 CAS 等一系列方法來保證一個變量在 多線程線程與核心不綁定 的情況下保持原子性。

2018年2月26日 09:56