Thread 方法:interrupt()、isInterrupted()、interrupted() 講解

前言:

三個方法,都是Thread中定義的方法,其中interrupted()是Thread中的靜態方法:
interrupt() : 給調用線程加入一箇中斷點,但是不會結束此線程。
isInterrupted():返回此線程的中斷狀態,但是不會移除此線程中斷狀態。
interrupted():返回的是當前線程的中斷狀態,會移除當前線程的中斷狀態

isInterrupted()、interrupted()區別

方法名 返回線程中斷狀態 是否會移除線程的中斷狀態 作用範圍【重點】
isInterrupted() 調用者線程
interrupted() 當前線程

代碼示例

  1. isInterrupted():
public class ThreadTest extends Thread{

    public static void main(String[] args) throws InterruptedException {
        ThreadTest threadTest = new ThreadTest();
        threadTest.start();

        // 1.給threadMethod 線程加入中斷點
        threadTest.interrupt();

        // 2. threadTest 線程中斷狀態
        System.out.println("第一次獲取threadTest的線程中斷狀態:" + threadTest.isInterrupted());
        System.out.println("第二次獲取threadTest的線程中斷狀態:" + threadTest.isInterrupted());
    }

    @Override
    public void run() {
        for (int i =0 ; i<10; i++){
            if(i == 5){
                // 3. 獲取到當前對象的線程中斷狀態
                System.out.println("第一次當前線程中斷狀態:" + Thread.currentThread().isInterrupted());
                System.out.println("第二次當前線程中斷狀態:" + Thread.currentThread().isInterrupted());

                // 5.根據中斷狀態 結束線程
                if (Thread.interrupted()){
                    return;
                }
            }
            System.out.println("i == " + i);
        }
    }
}

打印結果-執行順序可能不同:

第一次獲取threadTest的線程中斷狀態:true
第二次獲取threadTest的線程中斷狀態:true
i == 0
i == 1
i == 2
i == 3
i == 4
第一次當前線程中斷狀態:true
第二次當前線程中斷狀態:true

解析:
代碼 1 給 threadTest 加入線程中斷狀態, 通過被中斷的線程對象調用 isInterrupted() 獲取到線程的中斷狀態,代碼 2 3 多次獲取結果均爲 True, 最後通過代碼 5 結束正在運行的線程,實現主線程對其他線程的控制。

  1. interrupted() 是 Thread 內置靜態方法,調用 Thread.interrupted() :
public class ThreadTest extends Thread{

    public static void main(String[] args) throws InterruptedException {
        ThreadTest threadTest = new ThreadTest();
        threadTest.start();

        // 1.給threadMethod 線程加入中斷點
        threadTest.interrupt();

        // 2. threadTest 線程中斷狀態
        System.out.println("第一次獲取main的線程中斷狀態:" + Thread.interrupted());
        System.out.println("第二次獲取main的線程中斷狀態:" + Thread.interrupted());
    }

    @Override
    public void run() {
        for (int i =0 ; i<10; i++){
            if(i == 5){
                // 3. 獲取到當前對象的線程中斷狀態
                System.out.println("第一次當前線程中斷狀態:" + Thread.interrupted());
                System.out.println("第二次當前線程中斷狀態:" + Thread.interrupted());

                // 4.根據中斷狀態 結束線程
                if (Thread.interrupted()){
                    return;
                }
            }
            System.out.println("i == " + i);
        }
    }
}

打印結果:

第一次獲取main的線程中斷狀態:false
第二次獲取main的線程中斷狀態:false
i == 0
i == 1
i == 2
i == 3
i == 4
第一次當前線程中斷狀態:true
第二次當前線程中斷狀態:false
i == 5
i == 6
i == 7
i == 8
i == 9

解析:
代碼 1 是給 threadTest 線程加入線程中斷狀態,代碼 2 獲得的是當前線程 【main】的中斷狀態,因此爲 false
代碼 3 因爲 interrupted 會移除線程中斷狀態,所以第一次返回True 第二次返回 False。
代碼 5 interrupted 移除了線程中斷狀態,因此無法Ruturn

源碼:

爲什麼 兩者 之間會有區別那,看看源碼變知曉,不過多解釋:

// isInterrupted() 返回當前線程中斷狀態
public boolean isInterrupted() {
        return isInterrupted(false);
 }

// interrupted 獲取線程中斷狀態,並清除
public static boolean interrupted() {
        return currentThread().isInterrupted(true);
}

// 獲取當前線程。
public static native Thread currentThread();


 /**
  * 原生方法  獲取線程中斷狀態
   * ClearInterrupted 是否清除中斷狀態
   */
private native boolean isInterrupted(boolean ClearInterrupted);

注意: 當線程方法wiat、join、sleep三種方法之一,在起作用時,調用它的 interrupte()方法,會生成一個InterruptedException異常,因爲沒有佔用CPU 運行的線程是不可能給自己一箇中斷狀態置位的。
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章