并發(fā)——ReetrantLock —— 實現(xiàn)原理

1.ReetrantLock —— 實現(xiàn)原理:

實際組成:
獲取到鎖的:首先將status置為1,再一次獲取這個鎖的時候,在這個status上進(jìn)行++的操作。
沒有獲取到鎖的:有一個雙向鏈表,進(jìn)來的線程都掛在這個鏈表的尾部,保持頭指針為null

加鎖過程:
線程 1,2,3進(jìn)來,可以選擇公平鎖和非公平鎖的實現(xiàn)方式。

1)首先通過CAS去置位
        if 成功則占有鎖
            標(biāo)記自身占有鎖,把state置為1
        else
            再去嘗試 2)。
2)去獲取一個state 
        if (state ==0)
            執(zhí)行1)
        else if(state>0 && 占有的線程是當(dāng)前線程)
            state++;
        else
            沒有占有到鎖
3) 將自己放入一個等待的FIFO的隊列
        if(隊列的尾節(jié)點==null)
            初始化,直接放入尾節(jié)點
        else(不為空){    
            將上一個節(jié)點的next指向該節(jié)點,使該節(jié)點成為新的尾節(jié)點
              if(當(dāng)多個節(jié)點去占有尾節(jié)點){
                    whlie(每個線程放進(jìn)隊列里){
                          使用CAS去占有尾節(jié)點
                    }
              }         
        }
4 if(當(dāng)前節(jié)點的頭結(jié)點為Null){
              獲取鎖
              if(失敗){
                     waitStatus == SIGNAL;
                     該線程掛起;
                      遞歸去掛起后面的等待節(jié)點的線程,都是將每個節(jié)點對應(yīng)的waitStatus置為SIGNAL;
                  }
        }
注意:
AQS的FIFO的等待隊列給解決在鎖競爭方面的羊群效應(yīng)問題提供了一個思路:保持一個FIFO隊列,隊列每個節(jié)點只關(guān)心其前一個節(jié)點的狀態(tài),線程喚醒也只喚醒隊頭等待線程。


參考:
https://blog.csdn.net/yanyan19880509/article/details/52345422
http://www.importnew.com/24006.html
https://blog.csdn.net/jiangjiajian2008/article/details/52226189
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容