線程通信基礎(面向廁所編程)

一、sleep與wait的區別
先舉例,在理論
公廁(公廁的坑位是共享資源)中無論多少人(人是線程)排隊,只要你鎖好廁門(synchronized)就不會出現線程安全問題,無論排隊的多麼着急都要一個個來,鎖門期間(同步代碼塊內/同步方法內)調用sleep相當於你蹲坑期間睡着了,那麼門鎖(同步鎖)肯定不會自動打開,依然是鎖着的,除非時間到了你睡醒瞭然後該幹嘛幹嘛,否則只能通過粗暴的方式先把你叫醒(interreput方法)再說。wait相當於你禮讓他人,先主動打開門鎖(wait調用後連釋放同步鎖)讓出坑位給別人,然後主動去加入排隊蹲坑的大部隊邊睡覺(進程陷入阻塞態)邊等待。

二 、notify和notifyAll()
如果有人上完廁所,出來後看到睡眠中的排隊者們,可以通過只叫醒一個(notify),但叫醒的一定是憋的最着急的人(優先級最高的線程),被叫醒的人能立刻獲得坑位資源,也可以選擇一次性喚醒所有(notifyAll)排隊者,這時排隊者會一窩蜂湧入爭強坑位,可無論多麼激烈,只能有一個人搶佔坑位,優先級越高的線程搶到茅坑資源的概率越大

sleep和wait都是用來進行線程控制,都可以使線程阻塞
1 sleep(milliseconds)可以用時間指定來使他自動醒過來,如果時間不到你只能調用interreput()來強行打斷;wait()可以用notify()/notifyAll()直接喚起.
2. sleep是Thread類的靜態方法。 sleep的作用是讓線程休眠制定的時間,在時間到達時恢復,也就是說sleep將在接到時間到達事件事恢復線程 ; wait是Object的方法,也就是說可以對任意一個對象調用wait方法,調用wait方法將會將調用者的線程掛起,直到其他線程調用同一個對象的notify方法纔會重新激活調用者
3. sleep()是讓某個線程暫停運行一段時間,其控制範圍是由當前線程決定,wait()是由某個確定的對象來調用的。


sleep和wait的區別有:
1、這兩個方法來自不同的類分別是Thread和Object
2、最主要是sleep方法沒有釋放鎖,而wait方法釋放了鎖,使得其他線程可以使用同步控制塊或者方法。
3、wait,notify和notifyAll只能在同步控制方法或者同步控制塊裏面使用,而sleep可以在任何地方使用
4、sleep必須捕獲異常,而wait,notify和notifyAll不需要捕獲異常



經典案例,交替打印0~9

public class Accounter implements Runnable{
   
   

    private int index;
    @Override
    public void run() {
   
   
        String name = Thread.currentThread().getName();
        synchronized (this){
   
   
            while (index < 10){
   
   
                notify();
                System.out.println(name + "打印:" + index);
                index++;
                try {
   
   
                    wait();
                } catch (InterruptedException e) {
   
   
                    e.printStackTrace();
                }
            }
        }
    }

    public static void main(String[] args) {
   
   
        Accounter accounter = new Accounter();
        Thread thread = new Thread(accounter);
        Thread thread2 = new Thread(accounter);
        thread.start();
        thread2.start();
    }
}

推薦學習:消費者生產者案例

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章