更新時(shí)間:2020年12月08日15時(shí)41分 來源:傳智教育 瀏覽次數(shù):
JVM對(duì)Java的原生鎖做了哪些優(yōu)化?在Java之前,Monitor的實(shí)現(xiàn)完全依賴底層操作系統(tǒng)的互斥鎖來實(shí)現(xiàn),也就是我們剛才在問題二中所聞述的獲取/釋放鎖的邏輯。
由于Java層面的線程與操作系統(tǒng)的原生線程有映射關(guān)系,如果要將一個(gè)線程進(jìn)行阻塞或喚起都需要操作系統(tǒng)的協(xié)助,這就需要從用戶態(tài)切換到內(nèi)核態(tài)來執(zhí)行,這種切換代價(jià)十分昂貴,很耗處理器時(shí)間,現(xiàn)代JDK中做了大量的優(yōu)化。一種優(yōu)化是使用自旋鎖,即在把線程進(jìn)行阻塞操作之前先讓線程自旋等待一段時(shí)間,可能在等待期間其他線程已經(jīng)解鎖,這時(shí)就無再讓線程執(zhí)行阻塞操作,避免了用戶態(tài)到內(nèi)核態(tài)的切換。
再讓線程執(zhí)行阻塞操作,避免了用戶態(tài)到內(nèi)核態(tài)的切換。
現(xiàn)代JDK中還提供了三種不同的 Monitor實(shí)現(xiàn),也就是三種不同的鎖:
·偏向鎖( Biased Locking)
·輕量級(jí)鎖
·重量級(jí)鎖
這三種鎖使得JDK得以優(yōu)化Synchronized的運(yùn)行,當(dāng)JM檢測(cè)到不同的競(jìng)爭(zhēng)狀況時(shí),會(huì)自動(dòng)切換到適合的鎖實(shí)現(xiàn),這就是鎖的升級(jí)、降級(jí)。
·當(dāng)沒有競(jìng)爭(zhēng)出現(xiàn)時(shí),默認(rèn)會(huì)使用偏向鎖。
JVM會(huì)利用CAS操作,在對(duì)象頭上的Mark Word部分設(shè)置線程ID,以表示這個(gè)對(duì)象偏向于當(dāng)前線程,所以并不涉及真正的互斥鎖,因?yàn)樵诤芏鄳?yīng)用場(chǎng)景中,大部分對(duì)象生命周期中最多會(huì)被一個(gè)線程鎖定,使用偏斜鎖可以降低無競(jìng)爭(zhēng)開銷。
·如果有另一線程試圖鎖定某個(gè)被偏斜過的對(duì)象,JM就撤銷偏斜鎖,切換到輕量級(jí)鎖實(shí)現(xiàn)。
·輕量級(jí)鎖依賴CAS操作Mark Word來試圖獲取鎖,如果重試成功,就使用普通的輕量級(jí)鎖;否則,進(jìn)一步升級(jí)為重量級(jí)鎖。
猜你喜歡:
Mybatis執(zhí)行SQL命令是怎么實(shí)現(xiàn)的?
北京校區(qū)