本文主要总结在java中停止线程的方法
在java中有以下三种方法可以终止正在运行的线程:
1、使用退出标志
2、使用stop方法强行终止线程,但是不推荐,因为stop和suspend、resume一样都是过时的方法
3、使用interrup方法中断线程
停止不了的线程
本例将使用interrupt方法来停止进程,看看效果:
public class MyThread extends Thread {
@Override
public void run() {
super.run();
for (int i = 0; i < 1234; 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();
}
}
}
可以看出,线程没有停止
判断线程是否是停止状态
在java的SDK中,Thread.java类里提供了两种方法:
(1)this.interrupted():测试当前线程是否已经中断
(2)this.isInterrupted():测试线程是否已经中断
首先看一下interrupted()
实战验证一下:
public class MyThread extends Thread {
@Override
public void run() {
super.run();
for (int i = 0; i < 10000; 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();
System.out.println("是否停止1?="+thread.interrupted());
System.out.println("是否停止2?="+thread.interrupted()); } catch (InterruptedException e) {
System.out.println("main catch");
e.printStackTrace();
}
System.out.println("end!");
}
}
运行结果如下:
.......................
i=9998
i=9999
i=10000
是否停止1?=false
是否停止2?=false
end!
由于interrupted是测试当前线程,当前线程为main,一直没有中断,所以返回两个false
将代码修改一下:
public class Run {
public static void main(String[] args) {
Thread.currentThread().interrupt();
System.out.println("是否停止1?=" + Thread.interrupted());
System.out.println("是否停止2?=" + Thread.interrupted());
System.out.println("end!");
}
}
返回如下信息:
是否停止1?=true
是否停止2?=false
end!
由于interrupted方法有清除状态的功能,所以第二次返回false
再看看isInterrupted()方法
public class Run {
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!");
}
}
运行结果:
i=123367
i=123368
是否停止1?=true
是否停止2?=true
i=123369
i=123370
i=123371
i=123372
总结:
(1)this.interrupted():测试当前线程是否已经中断,执行后具有将状态标志清除为false的功能
(2)this.isInterrupted():测试线程是否已经中断,但不清除状态标志
能停止的线程--异常法
可以在线程中用for语句来判断一下线程是否是停止状态,如果是停止状态,则后面的代码不再运行即可
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!");
}
}
在sleep中停止
如果线程在sleep状态下停止线程,有什么效果呢?
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!");
}
}
运行结果:
run begin
end!
在沉睡中被停止!进入catch!false
java.lang.InterruptedException: sleep interrupted
at java.lang.Thread.sleep(Native Method)
at com.wuyudong.test1.MyThread.run(MyThread.java:9)
结果说明如果在sleep状态下停止线程,会进入catch语句,并且清除停止状态值,使之变成false
下面进行相反的操作,修改一下:
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(200000);
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!");
}
}
运行结果如下:
i=100000
run begin
先停止,再遇到了sleep!进入catch!
java.lang.InterruptedException: sleep interrupted
at java.lang.Thread.sleep(Native Method)
at com.wuyudong.test1.MyThread.run(MyThread.java:12)
能停止的线程--暴力停止
使用stop方法停止线程是十分暴力的
public class MyThread extends Thread {
private int i = 0;
@Override
public void run() {
super.run();
try {
while (true) {
i++;
System.out.println("i=" + i);
Thread.sleep(1000);
}
} catch (InterruptedException e) {
System.out.println("先停止,再遇到了sleep!进入catch!");
e.printStackTrace();
}
}
}
public class Run {
public static void main(String[] args) {
try {
MyThread thread = new MyThread();
thread.start();
Thread.sleep(8000);
thread.stop();
} catch (Exception e) {
e.printStackTrace();
}
}
}
运行结果如下:
i=1
i=2
i=3
i=4
i=5
i=6
i=7
i=8
方法stop与异常
调用stop方法的时候会抛出java.lang.ThreadDeath异常,但是通常此异常不需要显式地捕捉
public class MyThread extends Thread {
private int i = 0;
@Override
public void run() {
super.run();
try {
while (true) {
i++;
System.out.println("i=" + i);
Thread.sleep(1000);
}
} catch (InterruptedException e) {
System.out.println("先停止,再遇到了sleep!进入catch!");
e.printStackTrace();
}
}
}
public class Run {
public static void main(String[] args) {
try {
MyThread thread = new MyThread();
thread.start();
Thread.sleep(8000);
thread.stop();
} catch (Exception e) {
e.printStackTrace();
}
}
}
使用return停止线程
将方法interrupt与return结合使用也能实现停止线程的效果
public class MyThread extends Thread {
private int i = 0;
@Override
public void run() {
super.run();
while(true){
if(this.isInterrupted()){
System.out.println("停止了!");
return;
}
System.out.println("timer="+System.currentTimeMillis());
}
}
}
public class Run {
public static void main(String[] args) throws InterruptedException{
try {
MyThread thread = new MyThread();
thread.start();
Thread.sleep(2000);
thread.interrupt();
} catch (Exception e) {
e.printStackTrace();
}
}
}
运行结果如下:
timer=1452841019023
timer=1452841019023
timer=1452841019023
timer=1452841019023
停止了!