九、Executor框架
- 2019 年 10 月 21 日
- 筆記
Executor框架
我們知道執行緒池就是執行緒的集合,執行緒池集中管理執行緒,以實現執行緒的重用,降低資源消耗,提高響應速度等。執行緒用於執行非同步任務,單個的執行緒既是工作單元也是執行機制,從JDK1.5開始,為了把工作單元與執行機制分離開,Executor框架誕生了,他是一個用於統一創建與運行的介面。Executor框架實現的就是執行緒池的功能。
【1】Executor框架結構圖解
1、Executor框架包括3大部分:
(1)任務。也就是工作單元,包括被執行任務需要實現的介面:Runnable介面或者Callable介面;
(2)任務的執行。也就是把任務分派給多個執行緒的執行機制,包括Executor介面及繼承自Executor介面的ExecutorService介面。
(3)非同步計算的結果。包括Future介面及實現了Future介面的FutureTask類。
Executor框架的成員及其關係可以用一下的關係圖表示:
2、Executor框架的使用示意圖:
3、Executor框架成員:
【2】ThreadPoolExecutor實現類
1、FixedThreadPool
public static ExecutorService newFixedThreadPool(int nThreads) { return new ThreadPoolExecutor(nThreads, nThreads, 0L, TimeUnit.MILLISECONDS, new LinkedBlockingQueue<Runnable>()); } public static ExecutorService newFixedThreadPool(int nThreads, ThreadFactory threadFactory) { return new ThreadPoolExecutor(nThreads, nThreads, 0L, TimeUnit.MILLISECONDS, new LinkedBlockingQueue<Runnable>(), threadFactory); }
FixedThreadPool是執行緒數量固定的執行緒池,適用於為了滿足資源管理的需求,而需要適當限制當前執行緒數量的情景,適用於負載比較重的伺服器。
可以看出它的實現就是把執行緒池最大執行緒數量maxmumPoolSize和核心執行緒池的數量corePoolSize設置為相等,並且使用LinkedBlockingQueue作為阻塞隊列,那麼首先可以知道執行緒池的執行緒數量最多就是nThread,只會在核心執行緒池階段創建,此外,因為LinkedBlockingQueue是無限的雙向隊列,因此當任務不能立刻執行時,都會添加到阻塞隊列中
注意:因為阻塞隊列是無限的雙向隊列,因此如果沒有調用shutDownNow()或者shutDown()方法,執行緒池是不會拒絕任務的,如果執行緒池中的執行緒一直被佔有,且不斷有請求到來,會導致大量的請求堆積,進而造成記憶體溢出系統崩潰。
2、SingleThreadExecutor
public static ExecutorService newSingleThreadExecutor() { return new FinalizableDelegatedExecutorService (new ThreadPoolExecutor(1, 1, 0L, TimeUnit.MILLISECONDS, new LinkedBlockingQueue<Runnable>())); } public static ExecutorService newSingleThreadExecutor(ThreadFactory threadFactory) { return new FinalizableDelegatedExecutorService (new ThreadPoolExecutor(1, 1, 0L, TimeUnit.MILLISECONDS, new LinkedBlockingQueue<Runnable>(), threadFactory)); }
SingleThreadExecutor是只有一個執行緒的執行緒池,常用於需要讓執行緒順序執行,並且在任意時間,只能有一個任務被執行,而不能有多個執行緒同時執行的場景。
3、CachedThreadPool
public static ExecutorService newCachedThreadPool() { return new ThreadPoolExecutor(0, Integer.MAX_VALUE, 60L, TimeUnit.SECONDS, new SynchronousQueue<Runnable>()); } public static ExecutorService newCachedThreadPool(ThreadFactory threadFactory) { return new ThreadPoolExecutor(0, Integer.MAX_VALUE, 60L, TimeUnit.SECONDS, new SynchronousQueue<Runnable>(), threadFactory); }
CachedThreadPool適用於執行很多短期非同步任務的小程式,或者是負載較輕的伺服器。
CachedThreadPool使用SynchronizedQueue作為阻塞隊列,SynchronizedQueue是不存儲元素的阻塞隊列,實現「一對一的交付」,也就是說,每次向隊列中put一個任務必須等有執行緒來take這個任務,否則就會一直阻塞該任務,如果一個執行緒要take一個任務就要一直阻塞知道有任務被put進阻塞隊列。
【3】ScheduledThreadPoolExecutor實現類
具體參見:點擊打開連接
【4】Future介面/FutureTask實現類
具體參見:點擊打開連接