java.lang.Thread 类分析
概述
Thread 类是 Java 并发编程的核心类,代表 JVM 中的一个执行线程。该类实现了 Runnable 接口,提供了创建、启动、控制线程的完整 API。
基本信息:
- 包:
java.lang - 修饰符:
public class - 实现接口:
Runnable - 文件大小: 约 2055 行
- 版权: Oracle (1994-2016)
核心字段
线程基本属性
| 字段 | 类型 | 说明 |
|---|---|---|
name | volatile String | 线程名称 |
priority | int | 线程优先级 (1-10) |
daemon | boolean | 是否为守护线程 |
group | ThreadGroup | 所属线程组 |
target | Runnable | 要执行的任务对象 |
contextClassLoader | ClassLoader | 上下文类加载器 |
线程状态相关
| 字段 | 类型 | 说明 |
|---|---|---|
threadStatus | volatile int | JVM 线程状态 (0=NEW) |
stillborn | boolean | 线程是否未能正常启动 |
tid | long | 线程唯一 ID |
threadSeqNumber | static long | 生成线程ID的序列号 |
线程本地存储
| 字段 | 类型 | 说明 |
|---|---|---|
threadLocals | ThreadLocalMap | ThreadLocal 变量映射 |
inheritableThreadLocals | ThreadLocalMap | 可继承的 ThreadLocal 变量 |
其他重要字段
| 字段 | 类型 | 说明 |
|---|---|---|
stackSize | long | 请求的栈大小 |
parkBlocker | volatile Object | LockSupport.park 的参数 |
blocker | volatile Interruptible | 阻塞 I/O 操作的对象 |
uncaughtExceptionHandler | UncaughtExceptionHandler | 未捕获异常处理器 |
优先级常量
java
public final static int MIN_PRIORITY = 1; // 最低优先级
public final static int NORM_PRIORITY = 5; // 默认优先级
public final static int MAX_PRIORITY = 10; // 最高优先级线程状态枚举 (State)
java
public enum State {
NEW, // 新建但未启动
RUNNABLE, // 可运行/正在运行
BLOCKED, // 阻塞等待监视器锁
WAITING, // 无限期等待
TIMED_WAITING,// 限期等待
TERMINATED // 已终止
}构造方法
8 个公共构造方法
| 构造方法签名 | 说明 |
|---|---|
Thread() | 创建无名线程,自动生成名称 "Thread-n" |
Thread(Runnable target) | 指定任务目标的线程 |
Thread(String name) | 指定名称的线程 |
Thread(ThreadGroup group, Runnable target) | 指定线程组和任务 |
Thread(ThreadGroup group, String name) | 指定线程组和名称 |
Thread(Runnable target, String name) | 指定任务和名称 |
Thread(ThreadGroup group, Runnable target, String name) | 指定线程组、任务和名称 |
Thread(ThreadGroup group, Runnable target, String name, long stackSize) | 额外指定栈大小 (1.4+) |
内部构造方法
java
Thread(Runnable target, AccessControlContext acc) // 继承访问控制上下文初始化流程
所有构造方法最终调用私有 init() 方法:
java
private void init(ThreadGroup g, Runnable target, String name,
long stackSize, AccessControlContext acc,
boolean inheritThreadLocals)初始化关键步骤:
- 验证名称非 null
- 确定线程组(优先使用 SecurityManager 指定的组)
- 安全检查(子类覆盖权限)
- 继承父线程属性(守护状态、优先级、类加载器)
- 继承
inheritableThreadLocals - 分配唯一线程 ID
核心方法
线程控制方法
start() - 启动线程
java
public synchronized void start()- 检查线程状态,确保只启动一次
- 将线程添加到线程组
- 调用 native 方法
start0()启动底层线程
run() - 线程入口
java
public void run()- 如果指定了
target,则执行target.run() - 否则空实现(子类应重写此方法)
exit() - 线程退出清理
java
private void exit()- 清理 ThreadLocal 变量
- 通知线程组线程已终止
- 清空引用字段以加速 GC
已废弃的危险方法
| 方法 | 废弃原因 |
|---|---|
stop() | 强制停止会导致锁释放,可能破坏对象一致性 |
stop(Throwable obj) | 同上,且可生成目标线程未准备的异常 |
suspend() | 死锁风险:目标线程持锁时挂起会阻塞所有访问者 |
resume() | 仅与 suspend() 配合使用,随 suspend() 一起废弃 |
destroy() | 从未实现,同样存在死锁风险 |
推荐替代方案: 使用标志位让线程自行停止,配合 interrupt() 中断等待
中断机制
interrupt()
java
public void interrupt()中断策略:
- 阻塞在
wait()/join()/sleep()→ 清除中断状态并抛InterruptedException - 阻塞在
InterruptibleChannel→ 关闭通道,设置中断标志,抛ClosedByInterruptException - 阻塞在
Selector→ 立即返回选择操作 - 其他情况 → 仅设置中断标志
isInterrupted() / interrupted()
java
public boolean isInterrupted() // 测试中断状态,不清除
public static boolean interrupted() // 测试当前线程中断状态,并清除等待与连接
join()
java
public final void join() // 等待线程死亡
public final synchronized void join(long millis)
public final synchronized void join(long millis, int nanos)- 基于
this.wait()循环实现 - 条件:
while(isAlive()) - 线程终止时调用
this.notifyAll()
优先级管理
java
public final void setPriority(int newPriority)
public final int getPriority()- 优先级范围:
MIN_PRIORITY(1)到MAX_PRIORITY(10) - 实际优先级受线程组最大优先级限制
- 新线程继承创建者优先级
名称管理
java
public final synchronized void setName(String name)
public final String getName()- 线程名称用于调试和识别
- 未指定时自动生成 "Thread-n"
守护线程
java
public final void setDaemon(boolean on)
public final boolean isDaemon()- 必须在
start()前调用 - JVM 在所有非守护线程结束时退出
- 新线程继承创建者的守护状态
线程信息查询
| 方法 | 返回值 |
|---|---|
getId() | 线程唯一 ID (long) |
getName() | 线程名称 |
getPriority() | 优先级 |
isAlive() | 是否存活 |
isDaemon() | 是否守护线程 |
getState() | 线程状态 (State 枚举) |
getThreadGroup() | 所属线程组 |
getContextClassLoader() | 上下文类加载器 |
getStackTrace() | 当前堆栈跟踪 |
getAllStackTraces() | 所有活跃线程的堆栈 (Map) |
静态工具方法
java
public static native Thread currentThread() // 获取当前线程
public static native void yield() // 提示调度器让出 CPU
public static native void sleep(long millis) // 休眠指定毫秒
public static native boolean holdsLock(Object obj) // 检查当前线程是否持有锁
public static int activeCount() // 估算活跃线程数
public static int enumerate(Thread[] tarray) // 复制活跃线程到数组
public static void dumpStack() // 打印当前线程堆栈未捕获异常处理 (JSR-166)
UncaughtExceptionHandler 接口
java
@FunctionalInterface
public interface UncaughtExceptionHandler {
void uncaughtException(Thread t, Throwable e);
}全局默认处理器
java
public static void setDefaultUncaughtExceptionHandler(UncaughtExceptionHandler eh)
public static UncaughtExceptionHandler getDefaultUncaughtExceptionHandler()线程级处理器
java
public void setUncaughtExceptionHandler(UncaughtExceptionHandler eh)
public UncaughtExceptionHandler getUncaughtExceptionHandler()处理优先级:
- 线程自己的
uncaughtExceptionHandler - 线程组的
uncaughtException()方法 - 全局默认处理器
内部类
WeakClassKey
用于 Caches.subclassAudits 缓存的弱引用键:
- 继承
WeakReference<Class<?>> - 保存身份哈希码以保证一致性
- 支持引用队列进行自动清理
Native 方法列表
java
private static native void registerNatives()
public static native Thread currentThread()
public static native void yield()
public static native void sleep(long millis)
private native void start0()
private native void stop0(Object o)
private native void interrupt0()
private native boolean isInterrupted(boolean ClearInterrupted)
public final native boolean isAlive()
private native void suspend0()
private native void resume0()
private native void setPriority0(int newPriority)
public static native boolean holdsLock(Object obj)
private native static StackTraceElement[][] dumpThreads(Thread[] threads)
private native static Thread[] getThreads()
private native void setNativeName(String name)安全机制
访问控制
checkAccess():检查当前线程是否有权修改目标线程- SecurityManager 存在时会进行权限校验
子类安全检查
isCCLOverridden(Class<?> cl):检查子类是否覆盖了敏感的 ClassLoader 方法auditSubclass(Class<?> subcl):反射检查子类方法- 缓存检查结果于
ConcurrentHashMap<WeakClassKey, Boolean>
权限要求
| 操作 | 所需权限 |
|---|---|
| 修改上下文 ClassLoader | enableContextClassLoaderOverride |
| 停止其他线程 | stopThread |
| 获取堆栈跟踪 | getStackTrace |
| 修改线程组 | modifyThreadGroup |
| 设置默认异常处理器 | setDefaultUncaughtExceptionHandler |
设计特点
1. 双重任务执行模式
- 直接继承
Thread并重写run() - 或传入
Runnable作为任务目标
2. 线程状态机
通过 threadStatus 字段追踪状态变化:
- 0 = NEW(未启动)
- 其他值由 JVM 管理
3. 继承性设计
子线程默认继承父线程的:
- 优先级
- 守护状态
- 上下文类加载器
inheritableThreadLocals
4. 资源清理
exit() 方法激进地清空所有引用字段,帮助 GC 快速回收
5. 线程安全
- 关键字段使用
volatile(如name,parkBlocker,blocker) - 关键方法使用
synchronized(如start(),setName(),join())
使用建议
✅ 推荐做法
- 优先实现
Runnable而非继承Thread - 使用
interrupt()中断线程 - 设置合理的线程名称便于调试
- 为关键线程设置未捕获异常处理器
- 使用
join()等待线程完成
❌ 避免做法
- 不要使用已废弃的
stop(),suspend(),resume() - 不要在启动后调用
setDaemon() - 不要对同一线程调用两次
start() - 不要依赖
yield()做同步控制 - 不要忽略
InterruptedException
版本历史
| 版本 | 新增内容 |
|---|---|
| JDK 1.0 | 基础 Thread 类 |
| 1.2 | Context ClassLoader |
| 1.4 | 栈大小参数、holdLock() |
| 5.0 | State 枚举、线程 ID、未捕获异常处理、堆栈跟踪 API |
| 6.0 | 中断机制增强 |
