Thread的interrupt機制

weixin_33797791發表於2019-01-27

執行緒打斷是自我打斷

當呼叫執行緒的interrupt()方法時,被打斷的執行緒不會立刻被打斷,只是它裡面的一個狀態被改變.

@Override
    public void run() {
      //執行緒被其他執行緒打斷時,但還會一直執行
        while (true) {
            //true
            System.out.println("執行緒是否被打斷:" + this.isInterrupted()); 
            //true
            System.out.println("執行緒確認是否被打斷:" + this.isInterrupted()); 
        }
    }

interrupted()會使中斷狀態重置

被中斷執行緒可以通過interrupted()對狀態進行檢測,如果是被中斷狀態時,返回true,然後注意,此時的中斷狀態會被重置到未被打斷狀態,因此,被中斷執行緒可以通過呼叫一次該值不做任何處理,讓自己不被中斷.

@Override
    public void run() {
        while (true) {
            //true
            System.out.println("執行緒是否被打斷:" + this.isInterrupted()); 
            //true
            System.out.println("執行緒確認是否被打斷:" + this.isInterrupted()); 

            //判斷是否被中斷
            if(Thread.interrupted()){
                System.out.println("執行緒被中斷");

                //此時返回 false
                System.out.println("Thread.interupted():"+Thread.interrupted());
                break;
            }
        }
    }

isInterrupted()方法不會重置清除狀態

內部呼叫本地方法 private native boolean isInterrupted(boolean ClearInterrupted); 引數為false.
而上面的interrupted()方法也是呼叫了這個本地方法,只不過引數為ture.

InterruptedException異常不代表執行緒被中斷

另外的執行緒呼叫一個正在sleep(),或者wait()的執行緒的interrupt方法時,此時被中斷執行緒會丟擲一個異常,說明在休眠的執行緒中斷是會被通知的,且此時的中斷狀態為false,也就是說中斷休眠的執行緒是不會成功的,所以執行緒還是要自我打斷的。

@Override
    public void run() {
        while (true) {
            try {
                Thread.sleep(1000);
            } catch (InterruptedException e) {
                System.out.println("捕獲中斷異常");
                //輸出 false
                System.out.println("執行緒確認是否被打斷:"+this.isInterrupted());

                //輸出true
                this.interrupt();
                System.out.println("是否被self打斷:"+this.isInterrupted());
                break;
            }
        }
    }

參考:https://blog.csdn.net/hayre/article/details/52957580

相關文章