JAVA線程池使用實例

一、JAVA線程池使用

在使用Java多線程時引入線程池技術可以大大提高程序性能。Java提供的線程池相關的類主要有四個:Executor、ExecutorService、ScheduledExecutorService和ThreadPoolExecutor。其中,使用ThreadPoolExecutor類可以對線程池進行靈活的設置,可以很好地適應各種場景。

二、JAVA線程池參數設置

在使用Java線程池時,可以根據實際情況對線程池進行參數設置,以達到最佳的程序性能。線程池的主要參數包括以下幾個方面:

1、corePoolSize

核心池大小,即線程池初始化後啟動的線程數量。如果當前線程數量小於核心池大小,則新建線程;否則會將任務放入任務隊列等待執行。

2、maximumPoolSize

最大線程數量,即線程池中最多同時執行的線程數量。當線程池中已有的線程數大於等於corePoolSize時,新任務到來時會將任務放入任務隊列中等待。當任務到來時任務隊列已滿且當前線程數小於maximumPoolSize,則新建線程執行該任務。當線程數已達到最大線程數且任務隊列已滿,則會根據所設置的RejectedExecutionHandler進行相應的拒絕處理。

3、keepAliveTime

線程空閑時間,即空閑線程的存活時間。當線程池中線程數量大於corePoolSize時,需要有一定的機制來回收空閑線程,以便於釋放系統資源。當空閑時間超過keepAliveTime時,空閑線程將被回收。

4、TimeUnit

空閑時間的時間單位。該項參數以TimeUnit枚舉類型傳入,可以設置為TimeUnit.SECONDS、TimeUnit.MINUTES、TimeUnit.HOURS等。

5、workQueue

任務隊列。當線程池中線程數量達到corePoolSize時,新任務到來會被放入任務隊列中。該任務隊列可以是SynchronousQueue、LinkedBlockingQueue、ArrayBlockingQueue等各種線程安全隊列,也可以根據需要自己實現。

6、threadFactory

線程工廠。用於創建新的線程對象。可以通過ThreadFactoryBuilder來創建一個線程工廠。

7、rejectedExecutionHandler

任務拒絕策略。當線程池中線程數量已達到maximumPoolSize並且任務隊列已經滿了時,需要有一種機制來處理新到達的任務。主要有四種處理方式:

  • AbortPolicy(默認):直接拋出RejectedExecutionException異常。
  • CallerRunsPolicy:任務由調用線程直接執行。
  • DiscardOldestPolicy:將等待時間最長的任務從隊列中移除,將新任務加入隊列中。
  • DiscardPolicy:直接丟棄該任務。

三、JAVA創建線程池

Java提供了四個線程池類,分別是:

  • FixedThreadPool
  • CachedThreadPool
  • SingleThreadExecutor
  • ScheduledThreadPool

1、FixedThreadPool

FixedThreadPool固定大小線程池,會一直新建線程直到線程達到線程池的最大大小,線程池中的線程都是活躍的,線程池中線程數量不會超過給定的數量,並且線程都是在空閑狀態下等待接收任務,所以線程利用率高。

public static ExecutorService newFixedThreadPool(int nThreads) {
    return new ThreadPoolExecutor(nThreads, nThreads,
                                      0L, TimeUnit.MILLISECONDS,
                                      new LinkedBlockingQueue());
}

2、CachedThreadPool

CachedThreadPool線程池的大小會根據執行的任務數量自動擴展和收縮,沒有核心線程數,超過60秒空閑的線程被終止並從緩衝池中刪除。適用於執行大量短期異步任務的情景。

public static ExecutorService newCachedThreadPool() {
    return new ThreadPoolExecutor(0, Integer.MAX_VALUE,
                                      60L, TimeUnit.SECONDS,
                                      new SynchronousQueue());
}

3、SingleThreadExecutor

SingleThreadExecutor單線程池中只有一個核心線程,該線程會按先進先出的方式執行任務,所以不需要考慮線程同步的問題。適用於需要排隊依次執行任務的情況。

public static ExecutorService newSingleThreadExecutor() {
    return new FinalizableDelegatedExecutorService
        (new ThreadPoolExecutor(1, 1,
                                    0L, TimeUnit.MILLISECONDS,
                                    new LinkedBlockingQueue()));
}

4、ScheduledThreadPool

ScheduledThreadPool定長線程池可以定時或周期性地執行任務。適用於需要執行定時任務的情況。

public static ScheduledExecutorService newScheduledThreadPool(int corePoolSize) {
    return new ScheduledThreadPoolExecutor(corePoolSize);
}

完整的Java線程池使用實例:

import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.TimeUnit;

public class ThreadPoolTest {

    public static void main(String[] args) throws Exception {

        ExecutorService executorService = Executors.newFixedThreadPool(2);

        executorService.execute(() -> {
            System.out.println("任務1開始執行");
            try {
                Thread.sleep(5000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            System.out.println("任務1執行完畢");
        });

        executorService.execute(() -> {
            System.out.println("任務2開始執行");
            try {
                Thread.sleep(3000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            System.out.println("任務2執行完畢");
        });

        executorService.execute(() -> {
            System.out.println("任務3開始執行");
            try {
                Thread.sleep(1000);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            System.out.println("任務3執行完畢");
        });

        executorService.shutdown();
        executorService.awaitTermination(1, TimeUnit.HOURS);

    }

}

原創文章,作者:小藍,如若轉載,請註明出處:https://www.506064.com/zh-hk/n/198629.html

(0)
打賞 微信掃一掃 微信掃一掃 支付寶掃一掃 支付寶掃一掃
小藍的頭像小藍
上一篇 2024-12-04 10:26
下一篇 2024-12-04 10:26

相關推薦

  • Java JsonPath 效率優化指南

    本篇文章將深入探討Java JsonPath的效率問題,並提供一些優化方案。 一、JsonPath 簡介 JsonPath是一個可用於從JSON數據中獲取信息的庫。它提供了一種DS…

    編程 2025-04-29
  • java client.getacsresponse 編譯報錯解決方法

    java client.getacsresponse 編譯報錯是Java編程過程中常見的錯誤,常見的原因是代碼的語法錯誤、類庫依賴問題和編譯環境的配置問題。下面將從多個方面進行分析…

    編程 2025-04-29
  • Java Bean加載過程

    Java Bean加載過程涉及到類加載器、反射機制和Java虛擬機的執行過程。在本文中,將從這三個方面詳細闡述Java Bean加載的過程。 一、類加載器 類加載器是Java虛擬機…

    編程 2025-04-29
  • Java騰訊雲音視頻對接

    本文旨在從多個方面詳細闡述Java騰訊雲音視頻對接,提供完整的代碼示例。 一、騰訊雲音視頻介紹 騰訊雲音視頻服務(Cloud Tencent Real-Time Communica…

    編程 2025-04-29
  • Java Milvus SearchParam withoutFields用法介紹

    本文將詳細介紹Java Milvus SearchParam withoutFields的相關知識和用法。 一、什麼是Java Milvus SearchParam without…

    編程 2025-04-29
  • Java 8中某一周的周一

    Java 8是Java語言中的一個版本,於2014年3月18日發佈。本文將從多個方面對Java 8中某一周的周一進行詳細的闡述。 一、數組處理 Java 8新特性之一是Stream…

    編程 2025-04-29
  • Java判斷字符串是否存在多個

    本文將從以下幾個方面詳細闡述如何使用Java判斷一個字符串中是否存在多個指定字符: 一、字符串遍歷 字符串是Java編程中非常重要的一種數據類型。要判斷字符串中是否存在多個指定字符…

    編程 2025-04-29
  • Python生成隨機數的應用和實例

    本文將向您介紹如何使用Python生成50個60到100之間的隨機數,並將列舉使用隨機數的幾個實際應用場景。 一、生成隨機數的代碼示例 import random # 生成50個6…

    編程 2025-04-29
  • VSCode為什麼無法運行Java

    解答:VSCode無法運行Java是因為默認情況下,VSCode並沒有集成Java運行環境,需要手動添加Java運行環境或安裝相關插件才能實現Java代碼的編寫、調試和運行。 一、…

    編程 2025-04-29
  • Java任務下發回滾系統的設計與實現

    本文將介紹一個Java任務下發回滾系統的設計與實現。該系統可以用於執行複雜的任務,包括可回滾的任務,及時恢復任務失敗前的狀態。系統使用Java語言進行開發,可以支持多種類型的任務。…

    編程 2025-04-29

發表回復

登錄後才能評論