JAVA线程中断

林欢喜 Java经验 发布时间:2025-12-15 16:55:17 阅读数:1476 1
下文笔者讲述java线程中断的简介说明,如下所示

java线程中断的简介

线程中断
    是Java 中协作式线程终止机制
     核心是通过设置线程的 中断标记
     让线程自身感知到中断信号后
    自行决定是否停止执行(而非强制终止)。

java中"中断标记"简介

  每个线程都有一个布尔类型
     中断状态(默认false)
        调用`thread.interrupt()`:
          将目标线程的中断标记设为 `true`;
        线程可通过方法检查自身/其他线程的中断状态
          并根据此情况做出响应

核心API

方法 作用 注意点
`thread.interrupt()` 设置目标线程的中断标记为 `true` 仅标记,不强制终止线程
`Thread.currentThread().isInterrupted()`检查当前线程的中断标记(不清除标记) 标记仍保留为 `true`
`Thread.interrupted()` 检查当前线程的中断标记(清除标记,重置为 `false`) | 静态方法,全局感知
抛出 `InterruptedException` 当线程在阻塞状态(sleep/wait/join)时被中断,
会抛出该异常,且自动清除中断标记
异常抛出后,标记变回 `false`

线程中断核心规则

1. 协作式而非强制: 
     JVM 不会因为线程被中断就直接终止它,
       需线程自身主动检查标记并处理;
2. 阻塞方法的特殊处理:
     若线程处于 `sleep()`、`wait()`、`join()` 等阻塞状态时被中断,
        会立即抛出 `InterruptedException`,
        并清除中断标记;
3. 中断标记的保留/清除**:
   - 非阻塞状态下调用 `interrupt()`:
        标记仅设置为 `true`
        不会自动清除
   - 阻塞状态下触发 `InterruptedException`
       标记会被自动清除。

常见使用场景

场景1:中断非阻塞线程(主动检查标记)

线程在循环中执行任务 
定期检查中断标记
若标记为`true`则退出

public class InterruptNonBlockingThread {
    public static void main(String[] args) throws InterruptedException {
        Thread taskThread = new Thread(() -> {
            // 循环执行任务,主动检查中断标记
            while (!Thread.currentThread().isInterrupted()) {
                System.out.println("线程执行中...");
                try {
                    Thread.sleep(500); // 模拟任务耗时
                } catch (InterruptedException e) {
                    // 捕获中断异常,标记已被清除,需手动再次中断以退出循环
                    System.out.println("阻塞时被中断,异常捕获");
                    Thread.currentThread().interrupt(); // 重新设置中断标记
                }
            }
            System.out.println("线程感知到中断,正常退出");
        });

        taskThread.start();
        // 主线程等待3秒后中断任务线程
        Thread.sleep(3000);
        taskThread.interrupt();
    }
}

场景2
中断阻塞线程(捕获InterruptedException)

线程因 `sleep()`/`wait()` 阻塞时被中断,
    会抛出异常,
    需在异常处理中决定是否退出

public class InterruptBlockingThread {
    public static void main(String[] args) {
        Thread blockedThread = new Thread(() -> {
            try {
                // 线程阻塞10秒
                Thread.sleep(10000);
            } catch (InterruptedException e) {
                System.out.println("阻塞线程被中断:" + e.getMessage());
                // 异常处理:可选择退出、重试或其他逻辑
                return; // 退出线程
            }
            System.out.println("线程未被中断,正常执行完成");
        });

        blockedThread.start();
        // 立即中断阻塞线程
        blockedThread.interrupt();
    }
}

关键注意事项

1. 不要忽略InterruptedException:
   捕获该异常后,若不处理(如仅打印日志),会导致中断信号被“吞掉”,线程无法感知中断;
   ✅ 正确做法:
      - 如需退出:捕获异常后直接 `return` 或 `break`;
      - 如需继续执行:重新调用 `Thread.currentThread().interrupt()` 恢复中断标记。

2. 中断已终止的线程无意义:
   若线程已执行完毕(状态为 TERMINATED),调用 `interrupt()` 不会产生任何效果。

3. 与 stop() 的区别(重要):
       `stop()`:强制终止线程,会导致线程持有的锁释放、资源未清理(如文件流未关闭),已被废弃;
       `interrupt()`:协作式中断,线程自行决定何时退出,保证资源安全清理。
总结
   Java 线程中断的本质是「中断标记」的协作机制:
      1. 其他线程通过 `interrupt()` 
            给目标线程"发信号"(设置标记)
      2. 目标线程通过 `isInterrupted()`/`interrupted()` 
            检查信号
      3. 若线程处于阻塞状态,
            信号会触发 `InterruptedException`(并清除标记)
      4. 目标线程根据信号自行决定是否退出
            保证程序的安全性和可控性
版权声明

本文仅代表作者观点,不代表本站立场。
本文系作者授权发表,未经许可,不得转载。

本文链接: https://www.Java265.com/JavaJingYan/202512/17657889508521.html

最近发表

热门文章

好文推荐

Java265.com

https://www.java265.com

站长统计|粤ICP备14097017号-3

Powered By Java265.com信息维护小组

使用手机扫描二维码

关注我们看更多资讯

java爱好者