概要:中断就是一种协商机制,调用中断方法后会给此线程添加中断标记,需要程序员自行轮询中断标记,并自行编写中断逻辑。
1 线程中断的三大方法
1.1 void interrupt()
中断线程(即将该线程的中断状态设置为true),并不会立即停止线程。
1.2 static boolean interrupted()
返回线程中断状态并清除中断状态(即输出当前线程的中断状态,并将中断状态置为false)。该方法为静态方法。
1.3 boolean isInterrupted()
判断当前线程是否被中断。底层与interrupted()方法都调用了本地方法isInterrupted(boolean ClearInterrupted),区别是interrupted()传入的ClearInterrupted为true,代表清除中断状态;isInterrupted()传的是false,代表不清除中断状态。
注:1. 只有在线程存活状态下调用interrupt()方法才是有意义的,线程非存活时时线程的中断状态是false;
2. 当线程阻塞调用wait()、sleep()、join()方法时调用了interrupt()中断方法,则会抛出异常InterruptedException并清除线程的中断状态。这种情况下需要在sleep()的catch中再次调用线程中断方法。
2 中断线程的三种方式
2.1 使用volatile停止一个线程
public class VolatileDemo {
static volatile boolean flag = false;
public static void main(String[] args) {
new Thread(() -> {
while (true) {
if (flag) {
System.out.println("线程中断");
break;
}
System.out.println("t1执行中");
}
}, "t1").start();
try {
Thread.sleep(20);
} catch (InterruptedException e) {
e.printStackTrace();
}
new Thread(() -> flag = true, "t2").start();
}
}
2.2 使用AtomicBoolean中断一个线程
public class AtomicBooleanDemo {
static AtomicBoolean ab = new AtomicBoolean(false);
public static void main(String[] args) {
new Thread(() -> {
while (true) {
if (ab.get()) {
System.out.println("线程中断");
break;
}
System.out.println("t1执行中");
}
}, "t1").start();
try {
Thread.sleep(20);
} catch (InterruptedException e) {
e.printStackTrace();
}
new Thread(() -> ab.set(true), "t2").start();
}
}
2.3 使用interrupt中断一个线程
public class InterruptDemo {
public static void main(String[] args) {
Thread t1 = new Thread(() -> {
while (true) {
if (Thread.currentThread().isInterrupted()) {
System.out.println("线程中断");
break;
}
System.out.println("t1执行中");
}
}, "t1");
t1.start();
try {
Thread.sleep(20);
} catch (InterruptedException e) {
e.printStackTrace();
}
new Thread(t1::interrupt, "t2").start();
}
}