一个简单例子搞懂 thread.interrupt() java

interrupt()简介

interrupt():通知线程中断。(不是中断线程,只是修改中断标记置true,线程正常执行)。

具体对一个线程调用thread.interrupt()有如下情况:

  • 当线程处于阻塞状态,比如wait(),sleep,join(),会抛出 InterruptedException 异常。
  • 当线程处于整除状态,设置中断标志位为false,线程整除运行不受任何影响

小坑

  • 当catch (InterruptedException e) {}捕获到中断异常后,会重新把标志位设置为true,导致thread.isInterrupted() 一直为false。
  • 另外,当线程死亡的时候调用isInterrupted()也为false;

那如何直到查看是否线程是否中断呢,调用
thread.isInterrupted() 判断是否中断,此方法不改变中断状态。

案例实操

配合wait(),sleep,join()并抛InterruptedException 异常的方式使用

public class InterruptTest {
    static volatile boolean flag=true;
    public static void main(String[] args) throws IOException, InterruptedException {
        CountDownLatch latch1 = new CountDownLatch(3);
        CountDownLatch latch2 = new CountDownLatch(3);

        Thread thread1 = new Thread(() -> {
            latch1.countDown();
            System.out.println("线程:" + Thread.currentThread().getName() + "开始执行");
            while (true) {
                try {
                    Thread.sleep(1000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                    System.out.println("线程:" + Thread.currentThread().getName() + "安全退出");
                    latch2.countDown();
                }
            }
        });
        thread1.start();


        Object obj = new Object();
        Thread thread2 = new Thread(() -> {
            try {
                latch1.countDown();
                synchronized (obj){
                    System.out.println("线程:" + Thread.currentThread().getName() + "开始执行");
                    obj.wait(); // 注意得在同步代码块中,需要报监视器异常
                }
            } catch (InterruptedException e) {
                e.printStackTrace();
                System.out.println("线程:" + Thread.currentThread().getName() + "安全退出");
                latch2.countDown();
            }
        });
        thread2.start();

        Object obj2=new Object();
        Thread thread3 = new Thread(() -> {
            try {
                latch1.countDown();
                synchronized (obj2){
                    System.out.println("线程:" + Thread.currentThread().getName() + "开始执行");
                    Thread.currentThread().join(); // 一直阻塞直到线程死亡,底层调用wait()方法进行阻塞,所以也要synchronized
                }
            } catch (InterruptedException e) {
                e.printStackTrace();
                System.out.println("线程:" + Thread.currentThread().getName() + "安全退出");
                latch2.countDown();
            }
        });
        thread3.start();

        latch1.await();
        System.out.println("线程:"+Thread.currentThread().getName()+":输入回车中断线程");
        System.in.read();
        thread1.interrupt(); // 将线程的中断状态置为false,导致抛出interrupted异常,并会重新置中断位为false
        thread2.interrupt();
        thread3.interrupt();

        Thread thread4 = new Thread(() -> {
            while (flag){}// 不能让线程终止了,当线程终止的时候isInterrupted()方法为false
        });
        thread4.start();
        thread4.interrupt();

        latch2.await();
        System.out.println("线程:"+Thread.currentThread().getName()+":输入回车验证中断状态");
        System.in.read();
        System.out.println("thread1是否中断:"+thread1.isInterrupted()); // false 因为InterruptedException异常被捕获后中断标志又记为false
        System.out.println("thread4是否中断:"+thread4.isInterrupted()); // true
        flag=false;
    }
}

线程终止的三种方式

一、正常结束
二、thread.stop()

非常危险,不推荐,相当于切断电源,停止run()方法接下来所有代码,包括catch,finally,会产生各种意想不到的方法

三、thread.interrupt()

总结

interrupt()改变线程的中断状态,可由当前线程或其他线程调用,当线程阻塞的时候还会抛出InterruptedException异常。可通过isInterrupted()判断线程是否中断。

参考一
参考二

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值