【多线程】Thread 类中线程的状态

目录

一、再谈线程状态

二、线程状态的作用


一、再谈线程状态

之前我们说到,操作系统的线程有两种比较常见的状态------就绪状态 和 阻塞状态。

Java 为了能够调度操作系统的线程重新封装了一个专门用于管理线程调度的 Thread 类,同时也给线程的状态重新封装。

以下是重新封装后的线程状态:

线程状态 说明
NEW(初始状态) 新建了一个 Thread 类对象,但是还未调用 start 方法,操作系统层面的线程还未正式被创建
RUNNABLE(就绪状态 / 运行状态) 新建 Thread 类对象之后调用了 start 方法,该线程处于就绪状态或者运行状态
BLOCKED(阻塞状态) 线程此时因为锁而阻塞
WAITING(等待状态) 线程处于等待状态,若未被其他线程显式唤醒将会无限等待
TIMED_WAITING(超时等待) 线程处于限时的等待状态,当等待的时间超过了限定的时间,线程将会停止等待并继续执行
TERMINATED(终止状态) 当线程的 run () 方法执行完成或者主线程执行完成时,线程处于终止状态。线程一旦终止就不可再生

在 IDEA 中查看线程的状态:

java 复制代码
public class Demo13_threadState {
    // 查看 Thread 类所有的线程状态
    public static void main1(String[] args) {
        for (Thread.State state : Thread.State.values()) {
            System.out.println(state);
        }
    }

    // NEW 状态
    public static void main2(String[] args) throws InterruptedException {
        Thread t = new Thread(() -> {
            while (true) {
                // 什么都不做
                try {
                    Thread.sleep(1000);
                } catch (InterruptedException e) {
                    throw new RuntimeException(e);
                }
            }
        });

        System.out.println(t.getState());
    }

    // RUNNABLE 状态
    public static void main3(String[] args) throws InterruptedException {
        Thread t = new Thread(() -> {
            while (true) {
                // 什么都不做
                try {
                    Thread.sleep(1000);
                } catch (InterruptedException e) {
                    throw new RuntimeException(e);
                }
            }
        });
        t.start();

        System.out.println(t.getState());
    }

    // TIMED_WAITING 状态
    public static void main4(String[] args) throws InterruptedException {
        Thread t = new Thread(() -> {
            while (true) {
                // 什么都不做
                try {
                    Thread.sleep(2000);
                } catch (InterruptedException e) {
                    throw new RuntimeException(e);
                }
            }
        });
        t.start();

        Thread.sleep(1000);
        System.out.println(t.getState());
    }
}

当我们运行 main4 的时候,可以使用 jconsole 程序来查看当前程序中线程的状态:

二、线程状态的作用

小编认为,理解线程状态 并 懂得查看和分析线程状态 是调试多线程程序的重要技能之一。

如果在业务中发现代码的某个逻辑出 bug 了,我们就可以观察线程的状态从而分析是哪里出问题了:

  1. 当程序出现 bug ,我们可以借助第三方工具如 jconsole 来查看当前程序中对应逻辑线程的状态;

  2. 根据线程的状态来分析出 bug 的可能性:

如果线程的状态是 TIMED_WAITING 或者 WAITING,就得考虑一下是不是代码中某个方法产生了线程等待且没有及时将线程显式唤醒;

如果线程的状态是 BLOCKED,就得考虑一下代码中是不是出现了死锁;

如果线程的状态是 RUNNABLE,那说明线程本身没有问题,就得考虑一下是不是代码中的某些逻辑条件没有按预期触发。

......

  1. 再看看线程的调用栈,找到出现问题的具体代码行。

然后就找出问题所在:原来程序是因为循环 sleep 导致的等待啊!

那么本文到此就先告一段落啦~


相关推荐
CV_J3 小时前
安装kibana
java·elasticsearch·spring cloud·docker·容器
码农水水5 小时前
国家电网Java面试被问:TCP的BBR拥塞控制算法原理
java·开发语言·网络·分布式·面试·wpf
qq_336313935 小时前
java基础-网络编程-TCP
java·网络·tcp/ip
咕噜咕噜啦啦6 小时前
Java期末习题速通
java·开发语言
盐真卿6 小时前
python2
java·前端·javascript
一嘴一个橘子7 小时前
mybatis - 动态语句、批量注册mapper、分页插件
java
组合缺一7 小时前
Json Dom 怎么玩转?
java·json·dom·snack4
危险、7 小时前
一套提升 Spring Boot 项目的高并发、高可用能力的 Cursor 专用提示词
java·spring boot·提示词
kaico20187 小时前
JDK11新特性
java
钊兵7 小时前
java实现GeoJSON地理信息对经纬度点的匹配
java·开发语言