Java线程中断是一种协作机制,设置线程的中断标志并不能直接终止该线程执行,而是被中断的线程根据中断状态自行处理。
API核心方法
实例方法interrupt
public void interrupt() {
//...
}
- main线程调用t.interrupt()方法,将线程t的中断标志位设置为true,线程t还会继续执行
- 线程t调用了wait/sleep/join方法被阻塞后,main线程调用t.interrupt()方法时,线程t会在阻塞处抛InterruptedException异常。可在抛异常处继续中断当前线程,便于t1线程根据中断状态自行处理
Thread t1 = new Thread(()->{
while (true) {
if(Thread.currentThread().isInterrupted()) {
System.out.println("t1线程被中断了, 程序结束!");
break;
}
try {
TimeUnit.MILLISECONDS.sleep(200);
} catch (InterruptedException e) {
Thread.currentThread().interrupt();
System.out.println(Thread.currentThread().getName() + " 被中断了");
}
System.out.println("----------hello");
}
}, "t1");
t1.start();
System.out.println("--------------" + t1.isInterrupted());
//休眠5毫秒
TimeUnit.MILLISECONDS.sleep(5);
t1.interrupt();
System.out.println("--------------" + t1.isInterrupted());
执行结果:
--------------false
--------------true
t1 被中断了
----------hello
t1线程被中断了, 程序结束!
实例方法isInterrupted
public boolean isInterrupted() {
return isInterrupted(false);//传递false,说明不清除中断标志
}
判断当前线程是否被中断
静态方法interrupted
public static boolean interrupted() {
return currentThread().isInterrupted(true);
}
检测当前线程是否中断。如果当前线程被中断,会清除中断标志位。
Thread t = new Thread(()->{
while (true){}
});
t.start();
t.interrupt();
System.out.println(t.isInterrupted());
System.out.println(t.interrupted());//获取当前线程的中断标志,当前线程是main线程
System.out.println(Thread.interrupted());//获取当前线程的中断标志,当前线程是main线程
System.out.println(t.isInterrupted());
执行结果:
true
false
false
true
应用实例
- 比如一个线程t调用Thread.sleep(3000),线程t会阻塞,要等到3秒后才能变为就绪状态,此时可以使用t.interrupt()方法,强制sleep方法抛出InterruptedException异常并返回,线程t就恢复到就绪状态。
Thread t = new Thread(()->{
System.out.println("run....");
try {
TimeUnit.SECONDS.sleep(10);
} catch (InterruptedException e) {
System.out.println("main线程中断了t线程");
}
System.out.println("阻塞后开始执行。。。");
});
t.start();
try {
TimeUnit.SECONDS.sleep(2);
} catch (InterruptedException e) {
e.printStackTrace();
}
t.interrupt();
结果分析:
run....
main线程中断了t线程
阻塞后开始执行。。。
思考
- 有哪些方法会抛InterruptedException异常 wait/join/sleep