- 在之前的文章中我們知道了線程池各個參數的含義,其中有個參數
handler
我們說了是拒絕策略,具體關於線程池的拒絕策略我們這篇文章來分析 - 首先我們要理解線程池的拒絕策略的作用,它是用來處理當線程池無法繼續處理更多的任務時的處理機制,那么首先我們要知道拒絕策略的觸發時機,我么們來看下面代碼:
ThreadPoolExecutor threadPoolExecutor =
new ThreadPoolExecutor(
1,
2,
1,
TimeUnit.MILLISECONDS,
new LinkedBlockingQueue<>(),
new ThreadPoolExecutor.DiscardOldestPolicy()
);
線程池的拒絕時機
- 第一種,當我們正常關閉線程池時也就是使用
shutdown
等方法,這時候即使線程池中還有未完成的任務正在執行,但是由於線程池已經關閉,所以這時候我們再繼續向線程池提交任務的話就會被拒絕 - 第二種,當線程池沒有能力再繼續處理提交的任務,如隊列已滿,最大線程數達到,這時候線程池就處於飽和狀態
在我們需要學習和了解的就是第二種,在實際開發中我們需要解決這種情況,關於線程池運行的流程可以看之前我們文章,也可關注 i-code.online 博客。
拒絕策略
- 首先我們知道線程池的拒絕策略參數的類型是
RejectedExecutionHandler
類型的,那么我們可以先來了解一下關於這個接口的關系
- 在上述類圖中我們可以看到
RejectedExecutionHandler
接口有四個實現類,同時都提供了無參構造函數,這四個實現類對應了不同的拒絕策略,都有各自的適用場景
AbortPolicy
拒絕策略:這種策略在拒絕任務時,會直接拋出一個類型為RejectedExecutionException
的RuntimeException
,讓你感知到任務被拒絕了,於是你便可以根據業務邏輯選擇重試或者放棄提交等策略。
DiscardPolicy
拒絕策略:這種策略是當任務提交時直接將剛提交的任務丟棄,而且不會給與任何提示通知,所以這種策略使用要慎重,因為有一定的風險,對我們來說根本不知道提交的任務有沒有被丟棄
DiscardOldestPolicy
拒絕策略:這種策略和上面相似。不過它丟棄的是隊列中的頭節點,也就是存活時間最久的
CallerRunsPolicy
拒絕策略:這種策略算是最完善的相對於其他三個,當線程池無能力處理當前任務時,會將這個任務的執行權交予提交任務的線程來執行,也就是誰提交誰負責,這樣的話提交的任務就不會被丟棄而造成業務損失,同時這種誰提交誰負責的策略必須讓提交線程來負責執行,如果任務比較耗時,那么這段時間內提交任務的線程也會處於忙碌狀態而無法繼續提交任務,這樣也就減緩了任務的提交速度,這相當於一個負反饋。也有利於線程池中的線程來消化任務
本文由AnonyStar 發布,可轉載但需聲明原文出處。
歡迎關注微信公賬號 :雲棲簡碼 獲取更多優質文章
更多文章關注筆者博客 :雲棲簡碼 i-code.online