多執行緒鎖公升級的過程

2021-10-08 05:19:40 字數 1449 閱讀 1173

鎖公升級的方向:無鎖——>偏向鎖——>輕量級鎖——>重量級鎖,並且膨脹方向不可逆。

為什麼會有偏向鎖?

多數synchronized方法,在很多情況下,只有乙個執行緒在執行;

例如:在stringbuffer中的一些syn 方法;在vector中的一些syn方法;

偏向鎖是jdk6中引入的一項鎖優化,大多數情況下,鎖不僅不存在多執行緒競爭,而且總是由同一執行緒多次獲得,為了讓執行緒獲得鎖的代價更低而引入了偏向鎖。偏向鎖會偏向於第乙個獲得它的執行緒,如果在接下來的執行過程中,該鎖沒有被其他的執行緒獲取,則持有偏向鎖的執行緒將永遠不需要同步。

如果明顯存在其它執行緒申請鎖,那麼偏向鎖將很快公升級為輕量級鎖。

自旋鎖原理非常簡單,如果持有鎖的執行緒能在很短時間內釋放鎖資源,那麼那些等待競爭鎖的執行緒就不需要做核心態和使用者態之間的切換進入阻塞掛起狀態,它們只需要等一等(自旋),等持有鎖的執行緒釋放鎖後即可立即獲取鎖,這樣就避免使用者執行緒和核心的切換的消耗。

指的是原始的synchronized的實現,重量級鎖的特點:其他執行緒試圖獲取鎖時,都會被阻塞,只有持有鎖的執行緒釋放鎖之後才會喚醒這些執行緒。

場景1: 程式不會有鎖的競爭。那麼這種情況我們不需要加鎖,所以這種情況下物件鎖狀態為無鎖。

場景2: 經常只有某乙個執行緒來加鎖。

加鎖過程:也許獲取鎖的經常為同乙個執行緒,這種情況下為了避免加鎖造成的效能開銷,所以並不會加實際意義上的鎖,偏向鎖的執行流程如下:

執行緒首先檢查該物件頭的執行緒id是否為當前執行緒;

a:如果物件頭的執行緒id和當前執行緒id一致,則直接執行**;

b:如果不是當前執行緒id則使用cas方式替換物件頭中的執行緒id,如果使用cas替換不成功則說明有執行緒正在執行,存在鎖的競爭,這時需要撤銷偏向鎖,公升級為輕量級鎖。

如果cas替換成功,則把物件頭的執行緒id改為自己的執行緒id,然後執行**。

執行**完成之後釋放鎖,把物件頭的執行緒id修改為空。

場景3: 有執行緒來參與鎖的競爭,但是獲取鎖的衝突時間很短。

當開始有鎖的衝突了,那麼偏向鎖就會公升級到輕量級鎖;執行緒獲取鎖出現衝突時,執行緒必須做出決定是繼續在這裡等,還是回家等別人打**通知,而輕量級鎖的路基就是採用繼續在這裡等的方式,當發現有鎖衝突,執行緒首先會使用自旋的方式迴圈在這裡獲取鎖,因為使用自旋的方式非常消耗cpu,當一定時間內通過自旋的方式無法獲取到鎖的話,那麼鎖就開始公升級為重量級鎖了。

場景4: 有大量的執行緒參與鎖的競爭,衝突性很高。

我們知道當獲取鎖衝突多,時間越長的時候,我們的執行緒肯定無法繼續在這裡死等了,所以只好先休息,然後等前面獲取鎖的執行緒釋放了鎖之後再開啟下一輪的鎖競爭,而這種形式就是我們的重量級鎖。

執行緒和鎖,鎖公升級

程式 qq.exe feiqiu.exe 這種靜靜的躺在硬碟的軟體 程序 當程式載入到記憶體進行執行的就是程序資源分配的基本單位 執行緒 是程式執行的基本單位 執行緒如何進行排程的?linux是執行緒排程器,os 作業系統 執行緒切換的概念是什麼?context switch cpu儲存現場執行新執...

多執行緒的鎖

由於併發的問題,需要加鎖 當多個執行緒同時進行任務時,為了保證不會有多個執行緒同時對同乙個資料進行操作造成不可預料的後果,所以有了鎖的概念,我們通過鎖來使多執行緒任務更加安全。lock threading.lock cond threading.condition lock lock 多執行緒的鎖例...

python多執行緒鎖 python的多執行緒程式設計之鎖

1 背景概述 在python中,要保證資料的正確性,並且自己對資料進行控制,對資料進行加鎖並且自己釋放鎖。多執行緒的主要目的為了提高效能與速度,用在無關的方向是最好的,例如在使用爬蟲的時候,可以使用多執行緒來進行爬取資料,因為在這些執行緒之間沒有需要共同操作的資料,從而在這個時候利用是最好的。如果需...