Java 的notify 可能導致死鎖原因詳解

? ? 假設有一個共享資源庫 ResourcePool,它內部維護了兩類資源:ResourceTypeAResourceTypeB。現在有兩個線程 Thread1Thread2,它們都需要從資源庫中分別獲取一種資源才能繼續執行。Thread1 需要 ResourceTypeAThread2 需要 ResourceTypeB。資源庫提供了等待和通知機制,允許線程在資源不可用時等待,并在資源變為可用時得到通知。

初始條件
  • ResourcePool?中?ResourceTypeA?和?ResourceTypeB?都不可用。
  • Thread1?首先到達,開始等待?ResourceTypeA
  • Thread2?隨后到達,開始等待?ResourceTypeB
死鎖發生過程
  1. 資源釋放與等待

    • ResourceTypeA?變為可用,此時?ResourcePool?應該通知等待的線程。
    • ResourcePool?使用?notify()?方法嘗試喚醒一個等待的線程。
  2. 錯誤的線程被喚醒

    • 假設?notify()?方法隨機喚醒了?Thread2?而不是?Thread1
    • Thread2?嘗試獲取?ResourceTypeB,但是它仍然不可用,因此?Thread2?無法繼續執行,它再次進入等待狀態。
  3. 正確的線程未被喚醒

    • Thread1,它實際上可以使用現在可用的?ResourceTypeA,卻沒有被喚醒,因此它繼續等待。
  4. 沒有更多的通知

    • 由于?ResourcePool?只調用了一次?notify(),并且沒有新的資源變為可用來觸發額外的通知,Thread1?將永遠等待下去,即使它需要的資源已經可用。
  5. 死鎖發生

    • Thread1?和?Thread2?都在等待,無法繼續執行,也無法喚醒對方,系統進入死鎖狀態。
死鎖的解決
  • 使用?notifyAll()?替代?notify(),這樣在?ResourceTypeA?變為可用時,所有等待的線程都會被喚醒。Thread1?和?Thread2?都有機會檢查它們等待的資源是否可用,并相應地繼續執行或者繼續等待。
  • 設計資源獲取邏輯時使用循環來檢查條件,并在條件不滿足時繼續等待(超時等待)。這樣即使被錯誤喚醒,線程也會再次檢查資源是否滿足其需求,并在不滿足時重新等待,而不是假設資源已經可用并進入死鎖狀態。

? ?通過這種方式,可以確保每個線程在其所需資源變為可用時能夠被喚醒并繼續執行,從而避免了死鎖的發生。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/714721.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/714721.shtml
英文地址,請注明出處:http://en.pswp.cn/news/714721.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

上位機圖像處理和嵌入式模塊部署(當前機器視覺新形態)

【 聲明:版權所有,歡迎轉載,請勿用于商業用途。 聯系信箱:feixiaoxing 163.com】 過去的機器視覺處理,大部分都是集中在上位機、或者是服務器領域,這種形式維持了很長的時間。這種業務形態下,無…

windows 11 藍牙突然消失

解決方法: 1.WinX,點擊設備管理器 2.選中藍牙,右鍵更新驅動。 3.然后就可以出現了,如下圖

Django多個app配置多個域名訪問

環境:Python 3.8.1 Django 2.2.12 項目目錄結構: CellMiddle -- 項目根目錄 ├─task --- 需求系統 │ ├─migrations │ ├─static │ └─templates ├─logs --- 日志目錄 ├─doc --- 文檔系統 │ ├─data │ ├─migrations │ ├─st…

程序員是如何看待“祖傳代碼”的?

目錄 ?編輯 程序員是如何看待“祖傳代碼”的? 一、什么是“祖傳代碼”? 二、“祖傳代碼”的利弊 1. 可以節省開發成本 2. 可能引入安全隱患 3. 可能增加系統的維護難度 三、祖傳代對程序員的影響 1. 豐富程序員的技能和知識 2. 提高程序員的創…

python筆記_進制

二進制 進位規則:滿2進1 范圍:0,1 符號:以0b和0B開頭 八進制 進位規則:滿8進1 范圍:0-7 符號:以0o和0O開頭 十進制 進位規則:滿10進1 范圍:0-9 十六進制 進位規則&#xff…

Python——Tchisla求解器(暴力搜索法)

Tchisla簡介 最近玩到一個挺有意思的數字解密小游戲《Tchisla》,其規則類似算24點,也是利用一些數學運算和初始數字計算出目標數字,與算24點不同的是,Tchisla允許不限次數地使用一種初始數字(1~9)&#xf…

【VSCODE修改代碼行間距】解決方案

在我們編碼的過程中,由于顯示字體和顯示器的不同,會需要調整行間距,在vscode默認的選項中沒有看到設定行間距的選項,不過,可以手動修改配置檔達到目的。 1.打開設置 2.打開配置檔,手動進行設定 3.在選項中添…

第七十二天 漏洞發現-Web框架中間件聯動GobyAfrogXrayAwvsVulmap

第72天 漏洞發現-Web框架中間件&聯動&Goby&Afrog&Xray&Awvs&Vulmap 知識點: 1、Bup簡單介紹&使用說明 2、Xray簡單介紹&使用說明 3、AWWS簡單介紹&使用說明 4、Goby簡單介紹&使用說明 5、Afrog簡單介紹&使用說明 6、…

帶你玩轉java封裝和繼承(上)

上次帶大家學習了java里面比較重要的知識點類和對象,而且我們知道java是一門面向對象的語言,有時一個程序里可能有很多類,那么這么多類他們之間有什么聯系嗎?今天就帶大家學習一下java類之間的關系。 什么是繼承: 我們…

Linux信號【systemV】

目錄 前言 正文: 1消息隊列 1.1什么是消息隊列? 1.2消息隊列的數據結構 1.3消息隊列的相關接口 1.3.1創建 1.3.2釋放 1.3.3發送 1.3.4接收 1.4消息隊列補充 2.信號量 2.1什么是信號量 2.2互斥相關概念 2.3信號量的數據結構 2.4…

lambda表達式 —— 過濾再排序未生效問題排查

背景 項目中有個場景&#xff0c;需要將一個列表先按要求過濾&#xff0c;再根據某字段排序。圖方便使用lambda表達式修改原列表將過濾和排序邏輯寫到一行&#xff0c;打印輸出列表發現過濾未生效。 代碼示例&#xff1a; List<Long> productIdList Arrays.asList(1L);…

向爬蟲而生---Redis 探究篇4<Redis主從復制(1)>

前言: 當涉及到Redis的高可用性和數據冗余時&#xff0c;主從復制是一個非常重要的概念。 在現代應用程序的開發中&#xff0c;數據的可靠性和高可用性是至關重要的。當涉及到數據冗余和故障恢復時&#xff0c;Redis主從復制成為一個必不可少的工具和技術。Redis主從復制是一…

藍橋杯-單片機組基礎5——外部中斷與LED的控制(附小蜜蜂課程代碼)

藍橋杯單片機組備賽指南請查看這篇文章&#xff1a;戳此跳轉藍橋杯備賽指南文章 本文章針對藍橋杯-單片機組比賽開發板所寫&#xff0c;代碼可直接在比賽開發板上使用。 型號&#xff1a;國信天長4T開發板&#xff08;綠板&#xff09;&#xff0c;芯片&#xff1a;IAP15F2K6…

自學軟件測試怎么學?

軟件測試是一個變得越來越受歡迎的行業&#xff0c;在IT行業里面&#xff0c;也是初學比較容易的。但對小白而言&#xff0c;怎樣學習才能做到快速入門&#xff0c;少走彎路呢&#xff1f; 步驟一&#xff1a;初學學軟件測試&#xff0c;要先搞懂這種問題 要想進入到軟件測試…

Android Duplicate class 排除重復類

一、起因&#xff1a; 在迭代開發的時候&#xff0c;發現2個ijk很多類重復。但又2個庫實現的功能是不一樣&#xff0c;目前不能合并。但又想保留2個功能。需要排除其中一個庫。 二、報錯如何下圖&#xff1a; 三、解決方法&#xff1a; 3.1 在terminal 也就是命令行處輸入 …

Golang 并發機制 CSP模型

Golang 并發機制 CSP模型 1 前言 go語言的最大兩個亮點&#xff0c;一個是 goroutine &#xff0c;一個就是 chan 了。二者合體的典型應用CSP&#xff0c;基本就是大家認可的并行開發神器&#xff0c;簡化了并行程序的開發難度&#xff0c;我們來看一下CSP。 2 CSP是什么 C…

在Windows 11中運行磁盤清理工具的9種方法,總有一種適合你

自Windows98以來,微軟在操作系統中包含了一個內置的清理工具。當用戶轉向第三方清理應用程序時,這個值得信賴的實用程序站穩了腳跟。微軟甚至宣布,第三方應用程序幾乎毫無用處,刪除注冊表項不是一個好主意。 磁盤清理工具可以幫助刪除臨時文件、舊的更新日志、縮略圖緩存和…

git安裝與使用4.3

一、git的安裝 1、下載git包 下載git包url&#xff1a;https://git-scm.com/download/win 下載包分為&#xff1a;64位和32位 2、點擊安裝包 2、選擇安裝路徑 3、 點擊下一步 4、點擊next 5、點擊next 6、點擊next 7、 8、 9、 10、 11、 12、在桌面空白處&#xff0c;右鍵…

【SpringBoot】測試單元使用多線程

&#x1f4dd;個人主頁&#xff1a;五敷有你 &#x1f525;系列專欄&#xff1a;SpringBoot ??穩重求進&#xff0c;曬太陽 問題產生 今天學習了樂觀鎖&#xff0c;但在測試單元執行多線程的時候出現了問題&#xff0c;多線程并沒有直接結果 在控制臺沒有任何輸出…

KubeSphere平臺安裝系列之二【Linux單節點部署KubeSphere】(2/3)

**《KubeSphere平臺安裝系列》** 【Kubernetes上安裝KubeSphere&#xff08;親測–實操完整版&#xff09;】&#xff08;1/3&#xff09; 【Linux單節點部署KubeSphere】&#xff08;2/3&#xff09; 【Linux多節點部署KubeSphere】&#xff08;3/3&#xff09; **《KubeS…