1. 程式人生 > >停止執行緒方法(interrupt)

停止執行緒方法(interrupt)

java中有三種停止執行緒方法

1)使用退出標誌,使執行緒正常退出,也就是當run方法完成後執行緒終止。

2)使用stop方法方法強行終止執行緒,但是不推薦使用這個方法,應為stop不安全而且已經被廢棄的方法,還有suspend和resume都是廢棄的方法。

3)使用interrupt方法中斷執行緒。

講解第三種interrupt()方法 僅僅使房錢執行緒中打了一個停止的標記,並不是真的停止執行緒。程式碼如下:

public class MyThread extends Thread {

@Override

public void run() {

super.run();

for (int i = 0; i < 500000; i++) {

System.out.println("i=" + (i + 1));

}

}

}
public class Run {


public static void main(String[] args) {

try {

MyThread thread = new MyThread();

thread.start();

Thread.sleep(2000);

thread.interrupt();

} catch (InterruptedException e) {

System.out.println("main catch");

e.printStackTrace();

}

}


}

執行緒沒有停止,而是列印完i

再分析下執行緒是否是停止的狀態

this.interrupted() 測試當前執行緒是否已經中斷。

this.isInterrupted()測試執行緒是否已經中斷。

兩者區別:(小白還是不懂,如果大神們知道還請您給我留個言解答下☺)

如下程式碼展示:

public class MyThread extends Thread {

@Override

public void run() {

super.run();

for (int i = 0; i < 50000; i++) {

System.out.println("i=" + (i + 1));

}

}

}



public class Run {

public static void main(String[] args) {

try {

MyThread thread = new MyThread();

thread.start();

Thread.sleep(1000);

thread.interrupt();

//Thread.currentThread().interrupt();

System.out.println(thread.getName()+ " 是否停止1?="+thread.interrupted());

System.out.println(thread.getName()+ " 是否停止2?="+thread.interrupted());

} catch (InterruptedException e) {

System.out.println("main catch");

e.printStackTrace();

}

System.out.println("end!");

}




public class Run2 {

public static void main(String[] args) {

System.out.println(Thread.currentThread().getName());

Thread.currentThread().interrupt();

System.out.println("是否停止1?=" + Thread.interrupted());

System.out.println("是否停止2?=" + Thread.interrupted());

System.out.println("end!");

}

}



public class Run3 {

public static void main(String[] args) {

try {

MyThread thread = new MyThread();

thread.start();

Thread.sleep(1000);

thread.interrupt();

System.out.println("是否停止1?="+thread.isInterrupted());

System.out.println("是否停止2?="+thread.isInterrupted());

} catch (InterruptedException e) {

System.out.println("main catch");

e.printStackTrace();

}

System.out.println("end!");

}

}

結果圖:

1:停止執行緒(異常法)

public class MyThread extends Thread {

@Override

public void run() {

super.run();

for (int i = 0; i < 500000; i++) {

if (this.interrupted()) {

System.out.println("已經是停止狀態了!我要退出了!");

break;

}

System.out.println("i=" + (i + 1));

}

}

}


public class Run {


public static void main(String[] args) {

try {

MyThread thread = new MyThread();

thread.start();

thread.sleep(2000);//執行緒睡2s 停止

// Thread.sleep(2000);

thread.interrupt();

} catch (InterruptedException e) {

System.out.println("main catch");

e.printStackTrace();

}

System.out.println("end!");

}

}

上面的程式碼會出現下面問題:並沒有真正的退出執行緒

public class MyThread extends Thread {

@Override

public void run() {

super.run();

for (int i = 0; i < 500000; i++) {

if (this.interrupted()) {

System.out.println("已經是停止狀態了!我要退出了!");

break;

}

System.out.println("i=" + (i + 1));

}

System.out.println("我被輸出,如果此程式碼是for又繼續執行,執行緒並未停止!");

}

}


public class Run {


public static void main(String[] args) {

try {

MyThread thread = new MyThread();

thread.start();

Thread.sleep(2000);

thread.interrupt();

} catch (InterruptedException e) {

System.out.println("main catch");

e.printStackTrace();

}

System.out.println("end!");

}


}

解決如下

public class MyThread extends Thread {

@Override

public void run() {

super.run();

try {

for (int i = 0; i < 500000; i++) {

if (this.interrupted()) {

System.out.println("已經是停止狀態了!我要退出了!");

throw new InterruptedException();//中斷異常

}

System.out.println("i=" + (i + 1));

}

System.out.println("我在for下面");

} catch (InterruptedException e) {

System.out.println("進MyThread.java類run方法中的catch了!");

e.printStackTrace();

}

}

}


public class Run {


public static void main(String[] args) {

try {

MyThread thread = new MyThread();

thread.start();

Thread.sleep(2000);

thread.interrupt();

} catch (InterruptedException e) {

System.out.println("main catch");

e.printStackTrace();

}

System.out.println("end!");

}


}

2:在沉睡中停止執行緒

public class MyThread extends Thread {

@Override

public void run() {

super.run();

try {

System.out.println("run begin");

Thread.sleep(200000);

System.out.println("run end");

} catch (InterruptedException e) {

System.out.println("在沉睡中被停止!進入catch!"+this.isInterrupted());

e.printStackTrace();

}

}

}


public class Run {


public static void main(String[] args) {

try {

MyThread thread = new MyThread();

thread.start();

Thread.sleep(200);

thread.interrupt();

} catch (InterruptedException e) {

System.out.println("main catch");

e.printStackTrace();

}

System.out.println("end!");

}


}

下面是先停止執行緒 再遇到sleep進入catch

public class MyThread extends Thread {

@Override

public void run() {

super.run();

try {

for(int i=0;i<100000;i++){

System.out.println("i="+(i+1));

}

System.out.println("run begin");

Thread.sleep(20000);

System.out.println("run end");

} catch (InterruptedException e) {

System.out.println("先停止,再遇到了sleep!進入catch!");

e.printStackTrace();

}

}

}


public class Run {

public static void main(String[] args) {

MyThread thread = new MyThread();

thread.start();

thread.interrupt();

System.out.println("end!");

}

}

3:使用stop()暴力停止執行緒。。會釋放當前物件持有的鎖

public class SynchronizedObject {


private String username = "a";

private String password = "aa";


public String getUsername() {

return username;

}


public void setUsername(String username) {

this.username = username;

}


public String getPassword() {

return password;

}


public void setPassword(String password) {

this.password = password;

}

        //注意這裡加同步方法 但是由於使用了stop方法 是物件釋放鎖

synchronized public void printString(String username, String password) {

try {

this.username = username;

Thread.sleep(100000);

this.password = password;

} catch (InterruptedException e) {

e.printStackTrace();

}

}


}



public class MyThread extends Thread {


private SynchronizedObject object;


public MyThread(SynchronizedObject object) {

super();

this.object = object;

}


@Override

public void run() {

object.printString("b", "bb");

}

}


public class Run {

public static void main(String[] args) {

try {

SynchronizedObject object = new SynchronizedObject();

MyThread thread = new MyThread(object);

thread.start();

Thread.sleep(500);

thread.stop();

System.out.println(object.getUsername() + " "

+ object.getPassword());

} catch (InterruptedException e) {

e.printStackTrace();

}

}

}

列印如下