最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

總結(jié)java多線程之互斥與同步解決方案

 更新時(shí)間:2021年05月13日 11:53:22   作者:DaHuangXiao  
文中總結(jié)了線程互斥與同步,synchronized使用細(xì)節(jié)及原理,Reentrylock使用細(xì)節(jié)等知識(shí),對(duì)解決Java多線程互斥與同步等問題很有效,,需要的朋友可以參考下

一、線程互斥與同步

互斥:指的是多個(gè)線程不能同時(shí)訪問共享變量
同步:指的是多個(gè)線程按指定的順序執(zhí)行操作

在同時(shí)有多個(gè)線程運(yùn)行過程中,如何達(dá)到互斥和同步呢?

  • 加鎖即可

在此使用黑馬筆記中room例子來說明鎖。(ps: 以前就了解鎖,但總會(huì)記亂,發(fā)現(xiàn)使用形象化記憶后就很清楚)

在這里插入圖片描述

解決互斥

  • 鎖就相當(dāng)于上圖的房子,里面放著會(huì)被并發(fā)訪問的共享變量
  • 此時(shí)綠色區(qū)域(owner)無線程,此時(shí)多個(gè)線程想并發(fā)訪問房子里的共享變量,那么只允許其中一個(gè)線程進(jìn)入房子訪問,并把房門鎖上。
  • 剩下的沒有拿到鎖的線程只能在entrylist中排隊(duì)
  • owner中的線程訪問結(jié)束后會(huì)離開房子,并告訴entrylist的線程可以進(jìn)房子了
  • entrylist的線程開始新一輪的掙鎖,如此反復(fù)
  • 這樣就能解決互斥的問題

解決同步

(這涉及到為什么wait(),notify()方法需要用鎖,就是因?yàn)橹挥杏昧随i才能完成同步,那么怎么完成的呢?)

  • 多個(gè)線程同時(shí)啟動(dòng),如果希望B線程在A線程之后執(zhí)行
  • 那么當(dāng)B先搶到鎖,即先進(jìn)入了房子,此時(shí)A只能在entrylist中排隊(duì)
  • 為了讓A先執(zhí)行,那么可以先讓B進(jìn)入藍(lán)色區(qū)域,即waitset中等待,并且把門打開,告訴entrylist中的線程可以進(jìn)來了
  • 那么A進(jìn)來后,執(zhí)行完任務(wù),臨走時(shí)通知waitset中的B,B再回到綠色區(qū)域執(zhí)行任務(wù)就能保證有序了
  • 這樣就能解決同步問題

那么room這個(gè)數(shù)據(jù)結(jié)構(gòu)其實(shí)就是synchronized的核心了,接下來總結(jié)synchronized原理的時(shí)候會(huì)一直用room的例子

二、synchronized

很多人對(duì)synchronized原理的理解也就停留在知道字節(jié)碼有個(gè)monitor關(guān)鍵字來管理鎖,再淺一點(diǎn)的只知道怎么用,再者懂得深一點(diǎn)的卻記不住。我之前就是想深入了解一下但覺得苦澀,就看不下去了,看了黑馬的筆記我覺得這玩意兒其實(shí)很簡(jiǎn)單,所以好的老師還是比較重要的。那么在此我也記錄一下怎么更好的去理解synchronized的底層原理

從字節(jié)碼我們可以知道synchronized的底層就是關(guān)聯(lián)了一個(gè)monitor,那么這玩意兒是個(gè)什么東西,怎么實(shí)現(xiàn)鎖的功能呢?

首先,可以把monitor的數(shù)據(jù)結(jié)構(gòu)簡(jiǎn)化成上圖的room,具體點(diǎn)描述如下圖

在這里插入圖片描述

  • synchronized(鎖對(duì)象)的時(shí)候,相當(dāng)于讓鎖對(duì)象綁定了一個(gè)monitor(具體綁定方法不打算在后面總結(jié))
  • 那么多個(gè)線程中方法涉及到該鎖對(duì)象時(shí),都會(huì)來訪問鎖對(duì)象對(duì)應(yīng)的monitor
  • 此時(shí)線程thread-2搶到了鎖,操作就是讓monitor中的owner字段指向thread-2線程,意味著當(dāng)前線程獲取到了基于該monitor的鎖
  • 其他沒搶到鎖的,monitor會(huì)將他們放在Entrylist中等待,這些線程只能在隊(duì)列中等著
  • thread-2線程完成操作后就會(huì)退出,并通知entrylist的線程重新?lián)屾i
  • 如果在執(zhí)行過程中,線程調(diào)用了wait()方法,monitor就會(huì)將他們放入waitset中等待別人喚醒
  • (看回room結(jié)構(gòu))owner進(jìn)入waitset后會(huì)把門打開,讓entrylist的線程進(jìn)來
  • 直到某時(shí)刻owner中有線程調(diào)用notify()方法,waitset中的線程才會(huì)被喚醒,喚醒后會(huì)進(jìn)入entrylist中重新?lián)屾i

以上就是synchronized的原理。有人就會(huì)問了,你說的這些文字我都懂啊,搞個(gè)圖擺在這也沒啥用。

接下來我將從上圖直接回答下面的常見的問題

wait()和notify()為什么都得在synchronized后使用?

  • wait()就是將線程放入waitset中,那么waitset是在room里面的,不上鎖怎么能進(jìn)room中?同理,不進(jìn)入room,在門外怎么使用notify()怎么能叫醒waitset中的線程?

wait()會(huì)釋放鎖嗎?

  • 廢話,不開門的話,怎么放線程進(jìn)來,就更別提喚醒了

notifyALL()為什么不會(huì)喚醒其他鎖對(duì)象的線程?

  • 進(jìn)哪個(gè)room才能叫哪個(gè)waitset,進(jìn)了Aroom當(dāng)然只能叫醒A的waiset了

說說synchronized的原理?

  •  把圖畫出來就行了

線程什么時(shí)候從runnable變成waiting,什么時(shí)候變成block?

  • 看圖,進(jìn)入waiset就是wait,所以調(diào)wait()就變成waiting狀態(tài)進(jìn)入entrylist就是block,所以被喚醒后以及沒搶到鎖都變block 。。。。。。。。。。。。

注意了,這里涉及monitor的原理都是synchronized最根本的原理,也稱重量級(jí)鎖,可以看到monitor會(huì)頻繁切換線程狀態(tài),效率比較低。后來synchronized改進(jìn)了,在使用monitor前還有好幾種方案,分別為偏向鎖,輕量鎖,以及自旋優(yōu)化。這部分也是面試常考點(diǎn),也容易記亂,但用圖例去記就很清楚。

那么接下來就說說synchronized的改進(jìn)

三、輕量鎖與偏向鎖

輕量鎖與偏向鎖的核心都是先不讓線程沖突的時(shí)候直接去找monitor,而是先用鎖對(duì)象的對(duì)象頭字段來解決沖突

(寫博客好累啊。。。算了我就總結(jié)一些自己覺得關(guān)鍵的地方吧)

輕量鎖

  • 對(duì)于輕量鎖而言,每個(gè)線程維護(hù)了一個(gè)鎖記錄,搶占鎖的過程就是用CAS將自己的信息與鎖對(duì)象的對(duì)象頭mark word部分交換
  • 這樣其他慢一步的線程CAS會(huì)失敗,就意識(shí)到鎖已經(jīng)被占了
  • 可重入只需要在占鎖的時(shí)候判斷鎖對(duì)象的markword記錄的是不是自己的線程id即可,是的話就能夠獲取鎖,也就是疊加一個(gè)鎖記錄
  • 釋放鎖就意味著刪除鎖記錄,直到鎖記錄清空,就將鎖對(duì)象頭部被修改的字段變回原樣
  • 輕量鎖是認(rèn)為不會(huì)有競(jìng)爭(zhēng),如果發(fā)生了線程競(jìng)爭(zhēng),鎖需要升級(jí),不然上述方法沒有像monitor的entrylist來管理其他競(jìng)爭(zhēng)暫時(shí)沒拿到鎖的線程
  • 鎖升級(jí)就是鎖膨脹,直接調(diào)monitor來管理,就將owner指向當(dāng)前線程,然后競(jìng)爭(zhēng)線程去entrylist排隊(duì)
  • 其中涉及自旋優(yōu)化,就是線程競(jìng)爭(zhēng)時(shí),第二個(gè)線程不用立刻去entrylist中,這樣又要涉及上下文切換,可以自旋一會(huì)看鎖能否搶到

偏向鎖

  • 輕量鎖每次占鎖都要用一次CAS來更新鎖對(duì)象頭,如果本來就沒啥競(jìng)爭(zhēng)那CAS就是無用的操作了
  • 為了解決這個(gè)問題,線程搶鎖成功后直接把自己的ID刻在鎖對(duì)象頭中,需要判斷重入時(shí)只需判斷ID是否相同即可

到此這篇關(guān)于總結(jié)java多線程之互斥與同步解決方案的文章就介紹到這了,更多相關(guān)java多線程之互斥與同步內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • 解決Eclipse發(fā)布到Tomcat丟失依賴jar包的問題

    解決Eclipse發(fā)布到Tomcat丟失依賴jar包的問題

    這篇文章介紹了如何在Eclipse中配置部署裝配功能,以確保在將Web項(xiàng)目發(fā)布到Tomcat服務(wù)器時(shí)不會(huì)丟失任何依賴jar包,通過手動(dòng)配置或使用構(gòu)建工具腳本,可以自動(dòng)化這個(gè)過程,提高開發(fā)效率和應(yīng)用程序的穩(wěn)定性,感興趣的朋友跟隨小編一起看看吧
    2025-01-01
  • SpringBoot之RabbitMQ的使用方法

    SpringBoot之RabbitMQ的使用方法

    這篇文章主要介紹了SpringBoot之RabbitMQ的使用方法,詳細(xì)的介紹了2種模式,小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過來看看吧
    2018-12-12
  • Spring Cloud Feign 自定義配置(重試、攔截與錯(cuò)誤碼處理) 代碼實(shí)踐

    Spring Cloud Feign 自定義配置(重試、攔截與錯(cuò)誤碼處理) 代碼實(shí)踐

    這篇文章主要介紹了Spring Cloud Feign 自定義配置(重試、攔截與錯(cuò)誤碼處理) 實(shí)踐,本文通過實(shí)例代碼給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下
    2020-08-08
  • 最小樹形圖模板朱劉算法分享

    最小樹形圖模板朱劉算法分享

    這篇文章主要介紹了最小樹形圖模板朱劉算法,有需要的朋友可以參考一下
    2014-01-01
  • mybatis解析xml配置中${xxx}占位符的代碼邏輯

    mybatis解析xml配置中${xxx}占位符的代碼邏輯

    本文主要介紹了mybatis解析xml配置中${xxx}占位符的代碼邏輯,文中通過示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧<BR>
    2023-05-05
  • Java軟件設(shè)計(jì)模式之橋接模式詳解

    Java軟件設(shè)計(jì)模式之橋接模式詳解

    這篇文章主要介紹了Java軟件設(shè)計(jì)模式之橋接模式詳解,橋接模式也叫做橋梁模式,結(jié)構(gòu)型設(shè)計(jì)模式的一種,顧名思義,就是用來連接兩個(gè)部分,為被分離了的抽象部分和實(shí)現(xiàn)部分搭橋,需要的朋友可以參考下
    2023-07-07
  • Java如何按16進(jìn)制發(fā)送和接收TCP指令

    Java如何按16進(jìn)制發(fā)送和接收TCP指令

    這篇文章主要介紹了Java如何按16進(jìn)制發(fā)送和接收TCP指令問題,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教
    2023-09-09
  • Maven忽略單元測(cè)試及打包到Nexus的實(shí)現(xiàn)

    Maven忽略單元測(cè)試及打包到Nexus的實(shí)現(xiàn)

    我們的工程在打包發(fā)布時(shí)候,通常都需要忽略單元測(cè)試,以免因環(huán)境原因,無法通過單元測(cè)試而影響發(fā)布,本文主要介紹了Maven忽略單元測(cè)試及打包到Nexus的實(shí)現(xiàn),感興趣的可以了解一下
    2024-04-04
  • java解決請(qǐng)求跨域的兩種方法

    java解決請(qǐng)求跨域的兩種方法

    這篇文章主要為大家詳細(xì)介紹了java解決請(qǐng)求跨域的兩種方法,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2019-08-08
  • 解決spring cloud gateway 獲取body內(nèi)容并修改的問題

    解決spring cloud gateway 獲取body內(nèi)容并修改的問題

    這篇文章主要介紹了解決spring cloud gateway 獲取body內(nèi)容并修改的問題,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過來看看吧
    2020-12-12

最新評(píng)論

鹤峰县| 景洪市| 安塞县| 防城港市| 青河县| 丰镇市| 怀柔区| 汝阳县| 绥宁县| 普陀区| 永仁县| 延安市| 滨海县| 临湘市| 中江县| 新泰市| 静乐县| 靖宇县| 桂东县| 寿阳县| 六盘水市| 吉隆县| 水城县| 来安县| 武鸣县| 都匀市| 沂水县| 钟山县| 昆山市| 嘉禾县| 武鸣县| 上高县| 辰溪县| 繁峙县| 尼勒克县| 阳曲县| 昌乐县| 盖州市| 施甸县| 通许县| 遂川县|