ThreadPoolExecutor 七大核心參數
public ThreadPoolExecutor(
int corePoolSize, // 核心執行緒數
int maximumPoolSize, // 最大執行緒數
long keepAliveTime, // 非核心執行緒閒置存活時間
TimeUnit unit, // 時間單位
BlockingQueue workQueue, // 任務隊列
ThreadFactory threadFactory, // 執行緒工廠
RejectedExecutionHandler handler // 拒絕策略
)
參數配置策略與場景
1. 執行緒池大小控制
| 策略 | corePoolSize | maximumPoolSize | 適用場景 |
| 固定大小 | N | N | 長時間運行任務,CPU 密集型 |
| 緩衝無界 | N | Integer.MAX_VALUE | 大量短任務,SynchronousQueue |
| 有界隊列 | N | M (>N) | 需要背壓控制,防止 OOM |
2. 隊列選型指南
ArrayBlockingQueue:有界陣列隊列,公平鎖,適合固定緩衝
LinkedBlockingQueue:無界鏈表隊列(預設),高吞吐,**慎用於 maximumPoolSize > corePoolSize**(永不觸發擴容)
SynchronousQueue:零容量直接交付,**需搭配無界 maximumPoolSize**,適合快速任務
PriorityBlockingQueue:優先級隊列,任務需實作 Comparable
3. 拒絕策略選擇
AbortPolicy(預設):拋 RejectedExecutionException
CallerRunsPolicy:呼叫端執行緒執行任務,提供自然背壓
DiscardPolicy:靜默丟棄新任務
DiscardOldestPolicy:丟棄隊列最舊任務,嘗試重新提交
- 自訂:記錄日誌、持久化、轉發其他系統
4. 勾子方法應用
public class MonitoredThreadPool extends ThreadPoolExecutor {
@Override protected void beforeExecute(Thread t, Runnable r) {
super.beforeExecute(t, r);
// 記錄任務開始時間、執行緒資訊
}
@Override protected void afterExecute(Runnable r, Throwable t) {
super.afterExecute(r, t);
// 記錄耗時、異常、統計指標
}
@Override protected void terminated() {
super.terminated();
// 執行緒池完全終止時回調
}
}
並發集合深度解析
ConcurrentHashMap(JDK 8+ 改進)
- JDK 7:分段鎖,16 預設段,擴容需鎖全表
- JDK 8+:CAS + synchronized + 紅黑樹,細粒度鎖定 Node,擴容支援多執行緒協作
- 弱一致性迭代器:不拋
ConcurrentModificationException,反映迭代器建立時的狀態
- 原子操作:
putIfAbsent、computeIfAbsent、merge 等
CopyOnWrite 系列
- 寫時複製底層陣列,**讀完全無鎖**,適合「讀多寫極少」場景:事件監聽器、配置快照、白名單
- 迭代器遍歷快照,**不支援 remove/add/set**(拋
UnsupportedOperationException)
- 記憶體佔用大、寫入延遲高,大集合慎用
同步器快速選型
| 同步器 | 核心語義 | 典型場景 |
| Semaphore | 許可證計數 | 資源池限流、連接控制 |
| CountDownLatch | 倒數鎖(一次性) | 啟動等待、分階段同步 |
| CyclicBarrier | 循環柵欄(可重置) | 並行計算階段同步、多執行緒聚合 |
| Exchanger | 雙方資料交換 | 生產者-消費者雙緩衝、基因演算法 |
| Phaser | 階段同步器(JDK 7+) | 動態註冊/取消註冊的多階段任務 |
生產環境調優清單
- 根據任務類型(CPU/IO 密集)設定核心數:CPU 密集 ≈ 核心數;IO 密集 ≈ 核心數 * (1 + 平均等待/平均工作)
- 有界隊列 + CallerRunsPolicy 防止記憶體溢位
- 設定有意義的執行緒名稱前綴(
ThreadFactoryBuilder)便於除錯
- 監控指標:隊列長度、活躍執行緒數、完成任務數、拒絕任務數、任務等待/執行時間分佈
- 定期檢視
ThreadPoolExecutor 統計方法:getPoolSize()、getActiveCount()、getCompletedTaskCount()、getQueue().size()