Java多線程及線程池學習

常見的線程池:

newSingleThreadExecutor

ExecutorService threadPool = Executors.newSingleThreadExecutor();   

// 創建只含有單個線程的線程池,如果當前線程在執行任務時突然中斷,則會創建一個新的線程去替代它從而繼續執行任務。

單個線程的線程池,即線程池中每次只有一個線程工作,單線程串行執行任務
newFixedThreadExecutor(n)

ExecutorService threadPool = Executors.newFixedThreadPool(3);   

// 創建可以容納3個線程的線程池

創建一個固定大小的線程池。每次提交一個任務就會創建一個線程,直到創建的線程數量達到線程池的最大大小。線程池的大小一旦達到最大值就會保持不變。如果在所有線程都處於活動狀態時,這時再有其他任務提交,他們將等待隊列中直到有空閒的線程可用。如果任何線程由於執行過程中的故障而終止,將會有一個新線程將取代這個線程執行後續任務。
newCacheThreadExecutor(推薦使用)

ExecutorService threadPool = Executors.newCachedThreadPool();   

// 線程池的大小會根據執行的任務數量動態分配

CachedThreadPool會創建一個緩存區,將初始化的線程緩存起來,如果線程有可用的,就使用之前創建好的線程,如果沒有可用的,就會新創建線程。另外,終止並且從緩存中移除已有60秒未被使用的線程。
newScheduleThreadExecutor

ScheduledExecutorService threadPool = 

Executors.newScheduledThreadPool(3);   

// 效果類似於Timer定時器  

創建一個大小無限的線程池。此線程池支持定時以及週期性執行任務的需求。

(1)無論創建哪種線程池,必須要調用 ThreadPoolExecutor類。線程池類是 java.util.concurrent.ThreadPoolExecutor,常用構造方法爲: 

ThreadPoolExecutor(int corePoolSize, int maximumPoolSize, long keepAliveTime, TimeUnit unit, BlockingQueue workQueue, RejectedExecutionHandler handler) 

  • corePoolSize: 線程池維護核心線程的最少數量 
  • maximumPoolSize:線程池維護線程的最大數量 
  • keepAliveTime: 線程池維護線程所允許的空閒時間 
  • unit: 線程池維護線程所允許的空閒時間的單位 
  • workQueue: 線程池所使用的緩衝隊列 
  • handler: 線程池對拒絕任務的處理策略 

(2)一個任務通過 execute(Runnable r ) 方法被添加到線程池,任務就是一個 Runnable類型的對象,任務的執行方法就是 Runnable類型對象的run()方法。

 

(3)當一個任務通過execute(Runnable)方法 欲添加到線程池時: 

  • 如果此時線程池中的數量小於corePoolSize,即使線程池中的線程都處於空閒狀態,也要創建新的線程來處理被添加的任務。 
  • 如果此時線程池中的數量等於 corePoolSize,但是緩衝隊列 workQueue未滿,那麼任務被放入緩衝隊列。 
  • 如果此時線程池中的數量大於corePoolSize,緩衝隊列workQueue滿,並且線程池中的數量小於maximumPoolSize,建新的線程來處理被添加的任務。 
  • 如果此時線程池中的數量大於corePoolSize,緩衝隊列workQueue滿,並且線程池中的數量等於maximumPoolSize,那麼通過 handler所指定的策略來處理此任務。 

也就是說:處理任務的優先級爲: 

  • 核心線程池corePoolSize、任務隊列workQueue、最大線程maximumPoolSize,若三者都滿了,使用handler處理被拒絕的任務。 
  • 當線程池中的線程數量大於 corePoolSize時,如果某線程空閒時間超過keepAliveTime,線程將被終止。這樣,線程池可以動態的調整池中的線程數。 

(4)unit 可選的參數爲java.util.concurrent.TimeUnit中的幾個靜態屬性: 
NANOSECONDS、MICROSECONDS、MILLISECONDS、SECONDS。 


(5)workQueue 常用的可以是:java.util.concurrent.ArrayBlockingQueue


(6)handler有四個選擇: 

  • ThreadPoolExecutor.AbortPolicy() :拋出java.util.concurrent.RejectedExecutionException異常 
  • ThreadPoolExecutor.CallerRunsPolicy() :重試添加當前的任務,他會自動重複調用execute()方法 
  • ThreadPoolExecutor.DiscardOldestPolicy() :拋棄舊的任務 
  • ThreadPoolExecutor.DiscardPolicy() :拋棄當前的任務 
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章