Executor
為了更好的控制多線程,JDK提供了一套線程框架Executor,幫助開發人員有效地進行線程控制。它們都在java.util.concurrent包中,是JDK并發包的核心。其中有一個比較重要的類:Executors,他扮演這線程工廠的角色,我們通過Executors可以創建特定功能的線程池。
Executors創建線程池方法:
1: newFixedThreadPool()方法,該方法返回一個固定數量的線程池,該方法的線程數始終不變,當有一個任務提交時,若線程池中空閑,則立即執行,若沒有,則會被暫緩在一個任務隊列中等待有空閑的線程去執行。
newSingleThreadExecutor()方法,創建一個線程的線程池,若空閑則執行,若沒有空閑線程則暫緩在任務隊列中。
newCachedThreadPool()方法,返回一個可根據實際情況調整線程個數的線程池,不限制最大線程數量,若用空閑的線程則執行任務,若無任務則不創建線程。并且每一個空閑線程會在60秒后自動回收。
newScheduledThreadPool()方法,該方法返回一個SchededExcutorService對象,但該線程池可以指定線程的數量.
上面幾種方式底層都是通過ThreadPoolExecutor創建出來的。
自定義線程池使用詳情
參數說明 :corePoolSize 核心線程數量,也就是我們傳入的初始化創建的線程個數。maximumPoolSize 線程池最大線程數,keepAliveTime,TimeUnit unit這個兩個參數表示線程空閑時候的活躍時間。workQueue這個表示隊列,handler表示拒絕策略。
ThreadPoolExecutor(int corePoolSize,
int maximumPoolSize,
long keepAliveTime,
TimeUnit unit,
BlockingQueue<Runnable> workQueue,
RejectedExecutionHandler handler)
構造方法隊列是什么類型比較關鍵:
在使用有界隊列時: 若有新的任務需要執行,如果線程池實際線程數小于corePoolSize,則優先創建線程,若大于corePoolSize,則會將任務加入隊列,若隊列已滿,則在總線程數不大于maxiMumPoolSize的前提下,創建新的線程,若線程數大于maximumPoolSize,則執行拒絕策略。或其他自定義方式。
無界的任務隊列時: LinkedBlockingQueue。與有界隊列相比,除非系統資源耗盡,否則無界的任務隊列不存在任務入隊失敗的情況。當有新任務到來,系統的線程數小于corePoolSize時,則新建線程執行任務。當達到corePoolSize后,就不會繼續增加。若后續仍有新的任務加入,而有沒有空閑得線程資源,則任務直接進入隊列等待。若任務創建和處理的速度差異很大,無界隊列會保持快速增長,直到耗盡系統內存。
JDK拒絕策略:
AbortPolicy : 直接拋出異常組織系統正常的工作
CallerRunsPolicy : 只要線程池未關閉,該策略直接在調用者線程中,運行當前被丟棄的任務。
DiscardOlderstPolicy : 丟棄最老的一個請求,嘗試再次提交當前任務。
DiscardPolicy: 丟棄無法處理的任務,不給予任務處理。
如果需要自定義拒絕策略可以線程RejectedExecutionHandler 接口