什么是线程中断
java中的线程中断并不是指强制线程中断执行,而是指调用线程中断起到一个通知作用,让线程知道自己被中断了.至于线程是否应该继续执行下去,这个取决于业务代码本身
.而原来提供的stop()
方法,因为固有不安全性,现在已经不推荐使用该方式来实现线程中断.
线程中断相关方法
public void interrupt()
该方法作用就是中断线程.线程的中断标志将被标记为已中断.
public boolean isInterrupted()
该方法作用是检测线程是否已经中断.线程的中断状态不受该方法影响.
public static boolean interrupted() {
return currentThread().isInterrupted(true);
}
该方法同样也是用来检测线程是否中断的.但是需要注意的是,该方法会清除线程的中断状态.如果多次调用该方法.第一次返回true
,那么从第二次开始该方法将返回false
.具体实现代码如下:
private native boolean isInterrupted(boolean ClearInterrupted);
线程中断实战
线程收到中断信号,业务代码未处理中断失败
public class App1 {
public static void main(String[] args) throws InterruptedException {
Thread t1 = new Thread(() -> {
while (true){
Thread thread = Thread.currentThread();
boolean result = thread.isInterrupted();
System.out.println(String.format("当前线程:[%s],中断状态:[%b]",thread.getName(),result));
}
});
t1.setName("t1");
t1.start();
Thread.sleep(1000);
t1.interrupt();
}
}
上面代码的刚开始打印的结果为:当前线程:[t1],中断状态:[false]
,过1秒后结果打印当前线程:[t1],中断状态:[true]
,但是线程并没有停止运行.这正好说明了之前说的,java中的线程中断只是一个通知作用,并不会强制线程停止执行.
线程收到中断信号,业务代码处理了中断信号中断成功
public class App1 {
public static void main(String[] args) throws InterruptedException {
Thread t1 = new Thread(() -> {
while (true){
Thread thread = Thread.currentThread();
boolean result = thread.isInterrupted();
System.out.println(String.format("当前线程:[%s],中断状态:[%b]",thread.getName(),result));
if (result){
break;
}
}
});
t1.setName("t1");
t1.start();
Thread.sleep(1000);
t1.interrupt();
}
}
上面代码的刚开始打印的结果为:当前线程:[t1],中断状态:[false]
,过1秒后结果打印当前线程:[t1],中断状态:[true]
,而且该语句只会打印一次,然后程序停止运行.
线程处于WAITING或TIMED_WAITING下,业务代码未处理InterruptedException导致中断失败
public class App1 {
public static void main(String[] args) throws InterruptedException {
Thread t1 = new Thread(() -> {
while (true){
Thread thread = Thread.currentThread();
try {
Thread.sleep(3000);
} catch (InterruptedException e) {
e.printStackTrace();
}
boolean result = thread.isInterrupted();
System.out.println(String.format("当前线程:[%s],中断状态:[%b]",thread.getName(),result));
if (result){
break;
}
}
});
t1.setName("t1");
t1.start();
Thread.sleep(1000);
System.out.println("t1.getState() = " + t1.getState());
t1.interrupt();
}
}
上面的代码打印结果如下:
java.lang.InterruptedException: sleep interrupted
at java.lang.Thread.sleep(Native Method)
at com.buydeem.aqs.App1.lambda$main$0(App1.java:13)
at java.lang.Thread.run(Thread.java:745)
t1.getState() = TIMED_WAITING
当前线程:[t1],中断状态:[false]
当前线程:[t1],中断状态:[false]
线程处于TIMED_WAITING
状态下,然后发送中断信号.处理TIMED_WAITING
将抛出中断异常InterruptedException
,同时还会清除中断状态
.最后会一直打印当前线程:[t1],中断状态:[false]
,导致中断失败.
线程处于WAITING或TIMED_WAITING下,业务代码处理InterruptedException中断成功
public class App1 {
public static void main(String[] args) throws InterruptedException {
Thread t1 = new Thread(() -> {
while (true){
Thread thread = Thread.currentThread();
try {
Thread.sleep(3000);
} catch (InterruptedException e) {
e.printStackTrace();
System.out.println("收到中断异常,退出线程执行");
break;
}
boolean result = thread.isInterrupted();
System.out.println(String.format("当前线程:[%s],中断状态:[%b]",thread.getName(),result));
if (result){
break;
}
}
});
t1.setName("t1");
t1.start();
Thread.sleep(1000);
System.out.println("t1.getState() = " + t1.getState());
t1.interrupt();
}
}
interrupt()对不同状态下的线程的影响
- 在
NEW
和TERMINATED
中断线程没有什么意义,因为线程还未启动或者已经执行完成了. - 在
BLOCKED
和RUNNABLE
状态下,执行线程中断,只是会改变线程的中断状态,线程还是会继续执行. - 在
WAITING
和TIMED_WAITING
状态下,执行线程中断,线程会抛出InterruptedException
异常.
示例代码例子:InterruptDemo1~6
网友评论