通常狀況下,線程執行完成後就會結束,但有的時候咱們可能須要在它正常執行完成前就中止它,能夠考慮使用如下三種方法:java
使用Thread中的stop方法,這個方法已經被標爲已廢棄,不推薦使用,緣由是stop方法會當即終止線程並釋放持有的鎖,在多線程的狀況下可能會致使數據不一致的問題。多線程
自定義一個標誌,經過修改這個標誌的值來讓線程判斷是否須要退出。ide
使用線程中斷機制。線程
後面兩種方法有點相似,都是經過給線程發一個通知,而後讓線程去判斷是否能夠結束,而不是像stop方法那樣暴力的終止線程,下面介紹下後兩種方法的使用和區別。code
這裏定義了一個變量flag,主線程會在3秒後將flag設置爲false,當flag爲false的時候,run方法裏面的循環就會結束,線程也就中止了。it
public class MyThread extends Thread{ volatile boolean flag = true; @Override public void run() { while (flag){ System.out.println("do something..."); } } public static void main(String[] args) throws InterruptedException { MyThread myThread = new MyThread(); myThread.start(); Thread.sleep(3000); myThread.flag = false; } }
線程中斷有關的三個方法:io
這種方式與前面那種方式很相似,只是由判斷flag變爲判斷線程是否被中斷。class
public class MyThread extends Thread{ @Override public void run() { while (!isInterrupted()){ System.out.println("do something..."); } } public static void main(String[] args) throws InterruptedException { MyThread myThread = new MyThread(); myThread.start(); Thread.sleep(3000); myThread.interrupt(); } }
前面介紹的兩種方式使用起來很是的相似,可是中斷機制要更強,由於當循環體內出現了Thread.sleep()或者wait()這樣的操做時,自定義標誌的方式就只能等阻塞結束。而這兩個方法是能夠響應中斷的。變量
1.主線程在3秒後更改flag狀態,可是線程還處於sleep()阻塞中,須要等到sleep()時間結束也就是10秒後線程才中止。循環
public class MyThread extends Thread{ volatile boolean flag = true; @Override public void run() { while (flag){ try { Thread.sleep(10000); }catch (InterruptedException ex){ ex.printStackTrace(); } System.out.println("do something..."); } } public static void main(String[] args) throws InterruptedException { MyThread myThread = new MyThread(); myThread.start(); Thread.sleep(3000); myThread.flag = false; } }
2.處於sleep()阻塞中的線程若是被中斷就會拋出InterruptedException異常,此時它會清除中斷標記,因此須要捕獲該異常,並在異常處理中再次設置中斷標記。
public class MyThread extends Thread{ @Override public void run() { while (!isInterrupted()){ try { Thread.sleep(10000); }catch (InterruptedException ex){ //從新設置中斷標記 interrupt(); } System.out.println("do something..."); } } public static void main(String[] args) throws InterruptedException { MyThread myThread = new MyThread(); myThread.start(); Thread.sleep(3000); myThread.interrupt(); } }