自拍偷在线精品自拍偷,亚洲欧美中文日韩v在线观看不卡

Java線程同步如何才能排除阻塞

開發(fā) 后端
Java線程同步在不斷的學習中需要我們進行知識的延伸。下面我們就看看如何才能更好的進行相關知識延伸?希望大家有所收獲。

Java線程同步需要我們不斷的進行相關知識的學習,下面我們就來看看如何才能更好的在學習中掌握相關的知識訊息,來完善我們自身的編寫手段。希望大家有所收獲。

Java線程同步的優(yōu)先級代表該線程的重要程度,當有多個線程同時處于可執(zhí)行狀態(tài)并等待獲得 CPU 時間時,線程調(diào)度系統(tǒng)根據(jù)各個線程的優(yōu)先級來決定給誰分配 CPU 時間,優(yōu)先級高的線程有更大的機會獲得 CPU 時間,優(yōu)先級低的線程也不是沒有機會,只是機會要小一些罷了。

你可以調(diào)用 Thread 類的方法 getPriority() 和 setPriority()來存取Java線程同步的優(yōu)先級,線程的優(yōu)先級界于1(MIN_PRIORITY)和10(MAX_PRIORITY)之間,缺省是5(NORM_PRIORITY)。

Java線程同步

由于同一進程的多個線程共享同一片存儲空間,在帶來方便的同時,也帶來了訪問沖突這個嚴重的問題。Java語言提供了專門機制以解決這種沖突,有效避免了同一個數(shù)據(jù)對象被多個線程同時訪問。

由于我們可以通過 private 關鍵字來保證數(shù)據(jù)對象只能被方法訪問,所以我們只需針對方法提出一套機制,這套機制就是 synchronized 關鍵字,它包括兩種用法:synchronized 方法和 synchronized 塊。

1. synchronized 方法:通過在方法聲明中加入 synchronized關鍵字來聲明 synchronized 方法。如:

 

  1. public synchronized void accessVal(int newVal); 

synchronized 方法控制對類成員變量的訪問:每個類實例對應一把鎖,每個 synchronized 方法都必須獲得調(diào)用該方法的類實例 的鎖方能執(zhí)行,否則所屬線程阻塞,方法一旦執(zhí)行,就獨占該鎖,直到從該方法返回時才將鎖釋放,此后被阻塞的Java線程同步方能獲得該鎖,重新進入可執(zhí)行狀態(tài)。

這種機制確保了同一時刻對于每一個類實例,其所有聲明為 synchronized 的成員函數(shù)中至多只有一個處于可執(zhí)行狀態(tài)(因為至多只有一個能夠獲 得該類實例對應的鎖),從而有效避免了類成員變量的訪問沖突(只要所有可能訪問類成員變量的方法均被聲明為 synchronized)。

在 Java 中,不光是類實例,每一個類也對應一把鎖,這樣我們也可將類的靜態(tài)成員函數(shù)聲明為 synchronized ,以控制其對類的靜態(tài)成員變量的訪問。

synchronized 方法的缺陷:若將一個大的方法聲明為synchronized 將會大大影響效率,典型地,若將線程類的方 法 run() 聲明為 synchronized ,由于在線程的整個生命期內(nèi)它一直在運行,因此將導致它對本類任何 synchronized 方法 的調(diào)用都永遠不會成功。當然我們可以通過將訪問類成員變量的代碼放到專門的方法中,將其聲明為 synchronized ,并在主方法中調(diào)用來解決這一 問題,但是 Java 為我們提供了更好的解決辦法,那就是 synchronized 塊。

2. synchronized 塊:通過 synchronized關鍵字來聲明synchronized 塊。語法如下:

 

  1. synchronized(syncObject)  
  2. {  
  3. //允許訪問控制的代碼  

synchronized 塊是這樣一個代碼塊,其中的代碼必須獲得對象 syncObject (如前所述,可以是類實例或類)的鎖方能執(zhí)行,具體機制同前所述。由于可以針對任意代碼塊,且可任意指定上鎖的對象,故靈活性較高。

Java線程同步的阻塞

為了解決對共享存儲區(qū)的訪問沖突,Java 引入了同步機制,現(xiàn)在讓我們來考察多個Java線程同步對共享資源的訪問,顯然同步機制已經(jīng)不夠了,因為在任意時刻所要 求的資源不一定已經(jīng)準備好了被訪問,反過來,同一時刻準備好了的資源也可能不止一個。為了解決這種情況下的訪問控制問題,Java 引入了對阻塞機制的支 持。

阻塞指的是暫停一個Java線程同步的執(zhí)行以等待某個條件發(fā)生(如某資源就緒),學過操作系統(tǒng)的同學對它一定已經(jīng)很熟悉了。Java 提供了大量方法來支持阻塞,下面讓我們逐一分析。#t#

1. sleep() 方法:sleep() 允許指定以毫秒為單位的一段時間作為參數(shù),它使得線程在指定的時間內(nèi)進入阻塞狀態(tài),不能得到CPU 時 間,指定的時間一過,線程重新進入可執(zhí)行狀態(tài)。典型地,sleep() 被用在等待某個資源就緒的情形:測試發(fā)現(xiàn)條件不滿足后,讓線程阻塞一段時間后重新 測試,直到條件滿足為止。

2. suspend() 和 resume() 方法:兩個方法配套使用,suspend()使得線程進 入阻塞狀態(tài),并且不會自動恢復,必須其對應的resume() 被調(diào)用,才能使得線程重新進入可執(zhí)行狀態(tài)。典型 地,suspend() 和 resume() 被用在等待另一個線程產(chǎn)生的結(jié)果的情形:測試發(fā)現(xiàn)結(jié)果還沒有產(chǎn)生后,讓線程阻塞,另一個線程產(chǎn)生了結(jié)果 后,調(diào)用 resume() 使其恢復。

3. yield() 方法:yield() 使得線程放棄當前分得的 CPU 時間,但是不使線程阻塞,即線程仍處于可執(zhí)行狀態(tài),隨時可能再次分得 CPU 時間。調(diào)用 yield() 的效果等價于調(diào)度程序認為該Java線程同步已執(zhí)行了足夠的時間從而轉(zhuǎn)到另一個線程。

4. wait() 和 notify() 方法:兩個方法配套使用,wait() 使得線程進入阻塞狀態(tài),它有兩種形式,一種允許指定以毫秒為單位的 一段時間作為參數(shù),另一種沒有參數(shù),前者當對應的 notify() 被調(diào)用或者超出指定時間時Java線程同步重新進入可執(zhí)行狀態(tài),后者則必須對應 的 notify() 被調(diào)用。

初看起來它們與 suspend() 和 resume() 方法對沒有什么分別,但是事實上它們是截然不同的。區(qū)別的核心在于,前面敘述的所有方法,阻塞時都不會釋放占用的鎖(如果占用了的話),而這一對方法則相反。
 

責任編輯:張浩 來源: CSDN
相關推薦

2010-03-15 18:34:08

Java多線程

2010-03-16 14:32:51

Java系統(tǒng)線程組

2010-03-15 19:56:46

Java線程

2010-03-18 14:36:46

Java線程同步

2010-03-16 17:00:02

Java多線程支持

2019-07-23 11:01:57

Python同步異步

2012-10-10 10:00:27

同步異步開發(fā)Java

2017-11-14 16:43:13

Java虛擬機線程

2012-02-22 21:15:41

unixIO阻塞

2018-03-28 08:52:53

阻塞非阻塞I

2010-03-15 16:47:30

Java多線程同步

2024-09-23 17:15:28

Python并發(fā)并行

2010-03-16 17:39:36

Java多線程鎖

2010-03-17 18:21:54

Java多線程靜態(tài)數(shù)據(jù)

2010-03-15 19:21:37

Java多線程

2010-03-17 15:34:09

Java線程同步引用

2011-11-23 10:09:19

Java線程機制

2011-04-14 13:27:53

Synchronize多線程

2010-03-15 19:37:00

Java多線程同步

2010-01-21 11:27:30

linux多線程機制線程同步
點贊
收藏

51CTO技術棧公眾號