在JDK1.0中,可以用stop方法来终止,但是现在这种方法已经被禁用了,改用interrupt方法。
Thread.interrupt()方法不会中断一个正在运行的线程。它的作用是,在线程受到阻塞时抛出一个中断信号,这样线程就得以退出阻塞的状态。更确切的说,如果线程被Object.wait, Thread.join和Thread.sleep三种方法之一阻塞,那么,它将接收到一个中断异常(InterruptedException),从而提早地终结被阻塞状态。
中断异常
public static void main(String[] args) {
Thread thread = new Thread("thread") {
@Override
public void run() {
while(true){
try {
System.out.println("sleeping...");
Thread.sleep(2000);
} catch (InterruptedException ex) {
System.out.println("thread interrupted");
System.out.println(this.isInterrupted());
}
}
}
};
thread.start();
thread.interrupt();
}
结果:
sleeping...
thread interrupted
false
sleeping...
sleeping...
sleeping...
sleeping...
sleeping...
.
.
.
分析:
thread线程启动之后进行2秒的阻塞状态,这时候main线程执行thread线程的interrupt方法,设置thread线程的状态为可中断状态,
这个时候thread就会抛出异常InterruptedException,并且在抛出异常之后擦除调thread线程的中断状态又true为false。
public static void main(String[] args) {
Thread thread = new Thread("thread") {
@Override
public void run() {
while(true){
try {
System.out.println("sleeping...");
Thread.sleep(2000);
} catch (InterruptedException ex) {
System.out.println("thread interrupted");
System.out.println("before:" + this.isInterrupted());
Thread.currentThread().interrupt();
System.out.println("after:" + this.isInterrupted());
}
}
}
};
thread.start();
thread.interrupt();
}
结果:
sleeping...
thread interrupted
before:false
after:true
sleeping...
thread interrupted
before:false
after:true
.
.
.
分析:
thread线程启动之后进行2秒的阻塞状态,这时候main线程执行thread线程的interrupt方法,设置thread线程的状态为可中断状态,
这个时候thread就会抛出异常InterruptedException,并且在抛出异常之后擦除调thread线程的中断状态又true为false,所以before的状态为false,
这个时候又执行Thread.currentThread().interrupt()再一次将thread的中断状态设置为true,由于thread的while循环,thread进行sleep又抛出中断异常,这样循环往复。
总结:
在捕获InterruptedException异常之后如果只是想记录一条日志,那么就是不负责任的做法,因为在捕获InterruptedException异常的时候会将线程的中断标志置由trrue擦除掉改为false,这样就会导致方法其他链路获取该线程的中断状态有误,不能做出正确的响应。所以至少在捕获了InterruptedException异常之后,如果你什么也不想做,那么就将标志重新置为true,以便栈中更高层的代码能知道中断,并且对中断作出响应。