首先我們來看:
1.wait是object類的方法,也就是說,所有的物件都有wait方法
2.object中的wait方法被標為final,所以無法被重寫,原始碼如下:
public final native void wait(long timeout) throws interruptedexception;
3.native關鍵字修飾,表示這個方法使用其他語言實現。
4.丟擲interruptedexception,表示執行緒可能由已經終止的風險。
5.object提供了幾個wait方法:
看原始碼,第乙個long型別引數表示的就是執行緒等待時間,第二個int型別引數nanos表示納秒,1毫秒=1000微秒=1000000納秒。原始碼如下:
看完wait的原始碼,看一下停止wait的方法,notify和notifyall,與wait一樣,notify和notifyall也是object提供的方法,也是native方法,兩者的區別就在這個all上,下面詳細介紹一下:
1.notify :隨機 (據說與執行緒優先順序有關) 喚醒乙個登記集中的等待執行緒,該執行緒將從等待集中移除,重新加入對cpu時間片的競爭當中。
2.notifyall:喚起所有等待集中的等待執行緒,所有都加入對cpu時間片的爭奪中,先搶到鎖的先執行。
wait和notify和notifyall的使用場景:
已知wait有釋放同步鎖的效果,即當處於synchronized方法中的執行緒進入wait後,synchronized鎖將會自動被釋放,其他執行緒可以申請鎖、持有鎖,然後進入這個synchronized方法進行執行。
notify和notifyall後並不會返回之前持有的鎖,而是一起開始競爭鎖,誰先競爭到了,誰先執行。
這個方式是由thread提供的native方法,與wait一樣,丟擲了interruptedexception異常,看原始碼如下:
public static native void sleep(long millis) throws interruptedexception;
public static void sleep(long millis, int nanos)
throws interruptedexception
if (nanos 999999)
if (nanos >= 500000 || (nanos != 0 && millis == 0))
sleep(millis);
}
sleep與wait,在非多執行緒執行條件下的情況是一樣的,都是當前執行緒讓出執行機會,進入休眠/等待。但是在synchronized中就有一些不一樣了:
1.wait會釋放同步鎖,讓其他執行緒進入synchronized**塊執行。sleep不會釋放鎖,其他執行緒只能等待在synchronized**塊中進入sleep的執行緒醒後執行完畢才能競爭持有鎖。
2.wait可以被notify/notifyall等方法喚醒,繼續競爭cpu和鎖。sleep方法只能等待執行緒睡眠時間到繼續執行。
1.對於 sleep()方法,我們首先要知道該方法是屬於 thread 類中的。而 wait()方法,則是屬於 object 類中的。
2. sleep()方法導致了程式暫停執行指定的時間,讓出 cpu 該其他執行緒,但是
他的監控狀態依然 保持者
,當指定的時間到了又會自動恢復執行狀態。
3. 在呼叫 sleep()方法的過程中,
執行緒不會釋放物件鎖。
4. 而當
呼叫 wait()方法的時候,執行緒會放棄物件鎖
,進入等待此物件的
等待鎖定池
,只有針對此 物件呼叫 notify()方法後本執行緒才進入物件鎖定池準備獲取物件鎖進入執行狀態。
原理不同:
sleep是thread類的靜態方法,是執行緒用來控制自身流程的,它會使此執行緒暫停執行指定的時間,而把執行機會讓給其他的執行緒,等到計時時間到,此執行緒會自動甦醒.
wait是object類的方法,用於執行緒間的通訊,這個方法會使當前擁有該物件鎖的程序等待,直到其他執行緒呼叫notify方法才醒來,也可以指定時間自己醒來.
對鎖的處理機制不同
由於sleep方法的主要作用是讓執行緒休眠指定一段時間,在時間到時自動恢復,不涉及執行緒間的通訊,因此,呼叫sleep方法並不會釋放掉鎖.
但是呼叫wait方法的時候,執行緒會釋放掉它所占用的鎖,從而使執行緒所在物件中的其他synchronized資料可以被其他執行緒使用.
使用的區域不同
由於wait方法的特殊含義,所以它必須放在同步控制方法或者同步語句塊中使用,而sleep方法則可以放在任何地方使用.
異常的捕獲
sleep方法必須捕獲異常,而wait,notify以及notifyall不需要捕獲異常,在sleep的過程中,有可能別其他物件呼叫其interrupt(),產生interruptedexception異常.
sleep不會釋放鎖標誌,容易導致死鎖的發生,所以一般情況下,不推薦使用sleep方法,而是使用wait方法.
sleep和wait的區別
關鍵字 sleep wait 1 這兩個方法來自不同的類分別是thread和object 2 最主要是sleep方法沒有釋放鎖,而wait方法釋放了鎖,使得其他執行緒可以使用同步控制塊或者方法。3 wait,notify和notifyall只能在同步控制方法或者同步控制塊裡面使用,而sleep可以在...
sleep 和 wait的區別
1 這兩個方法來自不同的類分別是,sleep來自thread類,和wait來自object類。sleep是thread的靜態類方法,誰呼叫的誰去睡覺,即使在a執行緒裡呼叫了b的sleep方法,實際上還是a去睡覺,要讓b執行緒睡覺要在b的 中呼叫sleep。2 最主要是sleep方法沒有釋放鎖,而wa...
sleep和wait的區別
1 這兩個方法來自不同的類分別是,sleep來自thread類,和wait來自object類。sleep是thread的靜態類方法,誰呼叫的誰去睡覺,即使在a執行緒裡呼叫了b的sleep方法,實際上還是a去睡覺,要讓b執行緒睡覺要在b的 中呼叫sleep。2 最主要是sleep方法沒有釋放鎖,而wa...