java 線程狀態(tài) java線程鎖為什么鎖不住?
java線程鎖為什么鎖不???主要問題沒有給出完整的代碼和運(yùn)行結(jié)果,我分析這個(gè)代碼沒有問題,可以正確運(yùn)行。在這段代碼中,使用了savemoney類對(duì)象的鎖。這個(gè)對(duì)象在運(yùn)行時(shí)只有一個(gè)實(shí)例,這確保了在代碼執(zhí)
java線程鎖為什么鎖不???
主要問題沒有給出完整的代碼和運(yùn)行結(jié)果,我分析這個(gè)代碼沒有問題,可以正確運(yùn)行。
在這段代碼中,使用了savemoney類對(duì)象的鎖。這個(gè)對(duì)象在運(yùn)行時(shí)只有一個(gè)實(shí)例,這確保了在代碼執(zhí)行時(shí)只有一個(gè)線程可以獲得鎖。其他線程必須等待鎖保持線程釋放鎖,然后才能進(jìn)入。因此,主體需要補(bǔ)充如何在無法鎖定的情況下得出結(jié)論。
我還原了代碼并給出了如下運(yùn)行結(jié)果:
運(yùn)行的代碼應(yīng)該與所有者的代碼一致
運(yùn)行結(jié)果表明三個(gè)線程互斥執(zhí)行同步代碼塊。
歡迎批評(píng)指正。如果您認(rèn)為答案是好的,請(qǐng)您稱贊并注意^V^
Java并發(fā)線程的阻塞和喚醒可以分為以下幾類:
它是基于JVM的對(duì)象頭實(shí)現(xiàn)的。當(dāng)多線程競(jìng)爭(zhēng)相同的關(guān)鍵資源時(shí),它們會(huì)根據(jù)不同的鎖定機(jī)制(自旋鎖、輕/重鎖)阻塞和喚醒。
我跳過這里一會(huì)兒。一般的實(shí)現(xiàn)原理是基于對(duì)象的同步隊(duì)列與AQS非常相似。
關(guān)注AQS(抽象隊(duì)列同步器),因?yàn)檫@是JDK和契約實(shí)現(xiàn)的基礎(chǔ)(如鎖、阻塞隊(duì)列、倒計(jì)時(shí)鎖等)。
AQS基本上是通過可變狀態(tài)和等待隊(duì)列實(shí)現(xiàn)的。CAS先修改狀態(tài),失敗后放入等待隊(duì)列,通過locksupport掛起線程。
當(dāng)鎖所有者釋放鎖時(shí),它將通過locksupport喚醒等待隊(duì)列中的后續(xù)節(jié)點(diǎn),并讓它們?cè)俅螄L試獲取鎖(CAS修改狀態(tài))。
掌握AQS的原理對(duì)于理解JDK中的許多并發(fā)組件非常有幫助。
Java并發(fā)線程如何阻塞和喚醒?
下面簡(jiǎn)要說明以下原因:
鎖定是因?yàn)椴僮鞑皇窃拥摹W屛覀冇貌僮饕粊斫忉屗?。看下面兩個(gè)圖。
我這個(gè)操作需要
看上面的第二個(gè)圖,你能很清楚地理解這個(gè)過程嗎?
鎖定是為了確保上述三個(gè)步驟是原子操作。
回到問題上來,只有一個(gè)線程要寫,沒有競(jìng)爭(zhēng),所以不需要鎖定。
但是,如果你看第一張圖片,因?yàn)橹鲀?nèi)存和本地內(nèi)存的存在
在一個(gè)線程寫入后,其他線程無法立即看到它。這就是可見性問題。
添加volatile關(guān)鍵字后,它將在操作后強(qiáng)制工作內(nèi)存和主內(nèi)存同步,以確保其他線程可以立即看到它。