线程池监控与动态调优
Abstract
线程池不是配好就不管的,生产环境需要持续监控核心指标并根据负载动态调整参数。
监控指标
import java.util.concurrent.*;
public class ThreadPoolMonitor {
private final ThreadPoolExecutor executor;
public ThreadPoolMonitor(ThreadPoolExecutor executor) {
this.executor = executor;
}
public void logStatus() {
System.out.println("=== 线程池状态 ===");
System.out.println("核心线程数: " + executor.getCorePoolSize());
System.out.println("最大线程数: " + executor.getMaximumPoolSize());
System.out.println("活跃线程数: " + executor.getActiveCount());
System.out.println("池中线程数: " + executor.getPoolSize());
System.out.println("队列任务数: " + executor.getQueue().size());
System.out.println("已完成任务数: " + executor.getCompletedTaskCount());
System.out.println("总任务数: " + executor.getTaskCount());
System.out.println("=================");
}
}关键指标解读
| 指标 | 方法 | 说明 |
|---|---|---|
| 当前池大小 | getPoolSize() | 当前存活的线程数 |
| 活跃线程数 | getActiveCount() | 正在执行任务的线程数 |
| 核心线程数 | getCorePoolSize() | 可配置,核心线程不会因空闲被回收 |
| 队列积压 | getQueue().size() | 待处理任务数,持续增长需关注 |
| 完成任务数 | getCompletedTaskCount() | 累计完成数,结合时间可计算吞吐量 |
| 最大池大小 | getLargestPoolSize() | 历史峰值,反映并发高峰 |
队列积压是最重要的监控指标
队列持续增长意味着任务生产速度 > 消费速度,是 OOM 的前兆信号(见 JVM内存溢出预防)。
动态调优
ThreadPoolExecutor 提供了 set 方法,可以在运行时动态调整参数。
public class DynamicThreadPool {
private final ThreadPoolExecutor executor;
public DynamicThreadPool() {
this.executor = new ThreadPoolExecutor(
4, 8, 60L, TimeUnit.SECONDS,
new LinkedBlockingQueue<>(1000)
);
}
// 根据负载动态调整核心线程数
public void adjustCorePoolSize(int newSize) {
executor.setCorePoolSize(newSize);
}
// 根据队列长度动态调整
public void adjustBasedOnQueue() {
int queueSize = executor.getQueue().size();
int capacity = executor.getQueue().remainingCapacity() + queueSize;
if (queueSize > capacity * 0.8) {
// 队列积压超 80%,增加线程数
executor.setCorePoolSize(Math.min(
executor.getMaximumPoolSize(),
executor.getCorePoolSize() + 2
));
} else if (queueSize < capacity * 0.2
&& executor.getCorePoolSize() > 4) {
// 队列空闲,减少线程数
executor.setCorePoolSize(executor.getCorePoolSize() - 1);
}
}
}可动态调整的参数
| 参数 | 方法 | 说明 |
|---|---|---|
| 核心线程数 | setCorePoolSize(int) | 最常用的动态调整项 |
| 最大线程数 | setMaximumPoolSize(int) | 谨慎调大,防止创建过多线程 |
| 存活时间 | setKeepAliveTime(long, TimeUnit) | 调整非核心线程回收速度 |
| 拒绝策略 | setRejectedExecutionHandler(RejectedExecutionHandler) | 根据系统负载切换策略 |
| 线程工厂 | 不支持动态替换 | 只能在构造时指定 |
告警阈值建议
| 指标 | 告警阈值 | 说明 |
|---|---|---|
| 活跃线程占比 | activeCount / maximumPoolSize > 0.8 | 线程接近满负载 |
| 队列使用率 | queue.size() / capacity > 0.8 | 队列积压严重 |
| 拒绝次数 | > 0 (一旦发生就告警) | 任务被拒绝,需要立即响应 |
相关笔记
- ThreadPoolExecutor核心参数 — 构造参数详解
- Java线程池创建方式 — 线程池创建与配置
- JVM内存溢出预防 — 线程池相关的 OOM 预防