Java核心技術(shù)-并發(fā)編程-線程與線程池

在現(xiàn)在互聯(lián)網(wǎng)項(xiàng)目中,經(jīng)常面對(duì)的是高并發(fā)的場(chǎng)景,而針對(duì)面對(duì)高并發(fā)的系統(tǒng)架構(gòu)主要在緩存、分布式數(shù)據(jù)庫、消息隊(duì)列、分布式部署等進(jìn)行分享。
如何提高單應(yīng)用的響應(yīng)能力就跟線程有莫大的關(guān)系了。本文將通過以下內(nèi)容進(jìn)行分享:

  • 任務(wù)
  • 線程
  • 線程狀態(tài)
  • 線程屬性
  • 線程池

Part-1:任務(wù)

//定義任務(wù):實(shí)現(xiàn)Runnable接口
public class LiftOff implements Runnable {
    protected int countDown = 10;
    private static int taskCount = 0;
    private final int id = taskCount++;
    public LiftOff() {    }
    public LiftOff(int countDown) {this.countDown = countDown;    }
    public String status() {
        return "#" + id + "(" + (countDown > 0 ? countDown : "LiftOff!") + ")";
    }
    @Override
    public void run() {
        while (countDown-- > 0) {
            System.out.print(status());
            Thread.yield();
        }
    }
}

Part-2:線程調(diào)用

Thread thread=new Thread(new LiftOff());
thread.start();

//線程初始化方法
public Thread(
    ThreadGroup group,  //線程分組,默認(rèn)是空
    Runnable target,    //線程執(zhí)行任務(wù)
    String name,        //線程名稱
    long stackSize      //線程棧大小,默認(rèn)是0表示忽略
) 

Part-3:線程狀態(tài)

新建、可運(yùn)行、被阻塞、等待、計(jì)時(shí)等待、被終止


線程狀態(tài)切換.png

Part-4:線程屬性

  • 優(yōu)先級(jí)
//線程優(yōu)先級(jí):最低1,最高10,默認(rèn)為5
t.setPriority(int newPriority)
  • 守護(hù)線程
t.setDaemon(true)

PS:當(dāng)程序僅剩下守護(hù)線程的時(shí)候,虛擬機(jī)就會(huì)退出

Part-5:線程池

構(gòu)建一個(gè)線程有一定代價(jià),因?yàn)樯婕芭c操作系統(tǒng)的交互。如果程序中創(chuàng)建大量生命周期很短的線程,應(yīng)該使用線程池(thread pool)。

  • 線程池創(chuàng)建基礎(chǔ)類
//Java線程池構(gòu)建底層方法:
public ThreadPoolExecutor(
    int corePoolSize,                   //線程池工作線程池大小
    int maximumPoolSize,                //線程池最大工作線程數(shù)
    long keepAliveTime,                 //非核心線程空閑等待時(shí)長
    TimeUnit unit,                      //非核心線程空閑等待時(shí)間單位
    BlockingQueue<Runnable> workQueue,  //線程池任務(wù)等待隊(duì)列
    ThreadFactory threadFactory,        //線程構(gòu)建工廠,默認(rèn)DefaultThreadFactory
    RejectedExecutionHandler handler    //
)
  • 默認(rèn)線程池創(chuàng)建方法
//java.util.concurrent.Executors 神明系統(tǒng)不同線程池
//固定線程池
public static ExecutorService newFixedThreadPool(int nThreads) {
    return new ThreadPoolExecutor(
        nThreads, 
        nThreads,
        0L, 
        TimeUnit.MILLISECONDS,
        new LinkedBlockingQueue<Runnable>());
}

//單線程實(shí)例線程池
public static ExecutorService newSingleThreadExecutor() {
    return new FinalizableDelegatedExecutorService(
        new ThreadPoolExecutor(
            1, 
            1,
            0L, 
            TimeUnit.MILLISECONDS,
            new LinkedBlockingQueue<Runnable>()));
}

//緩存線程池
public static ExecutorService newCachedThreadPool() {
    return new ThreadPoolExecutor(
            0, 
            Integer.MAX_VALUE,
            60L, 
            TimeUnit.SECONDS,
            new SynchronousQueue<Runnable>());
}

//計(jì)劃線程池
public static ScheduledExecutorService newScheduledThreadPool(int corePoolSize) {
    return new ScheduledThreadPoolExecutor(corePoolSize);
}

//單個(gè)核心計(jì)劃線程池
public static ScheduledExecutorService newSingleThreadScheduledExecutor() {
    return new DelegatedScheduledExecutorService
        (new ScheduledThreadPoolExecutor(1));
}
  • 線程池參數(shù)比較


    線程池參數(shù)差異.png
  • 拒絕策略

//執(zhí)行指定任務(wù)
public static class CallerRunsPolicy implements RejectedExecutionHandler {
//拋出異常:RejectedExecutionException
public static class AbortPolicy implements RejectedExecutionHandler {
//新任務(wù)直接丟棄
public static class DiscardPolicy implements RejectedExecutionHandler {
//將等待隊(duì)列頭部節(jié)點(diǎn)丟棄,將新任務(wù)放入隊(duì)尾
public static class DiscardOldestPolicy implements RejectedExecutionHandler {

Part-6:帶返回類型任務(wù)

  • 實(shí)現(xiàn)Callable<T>接口
import java.util.Random;
import java.util.concurrent.Callable;

public class RandomDataCallable implements Callable<Integer> {
    private final Random random = new Random();
    private final Integer randomLimit = 10000;

    @Override
    public Integer call() throws Exception {
        //模擬異步任務(wù)
        int randomResult = 0;
        do {
            Thread.currentThread().join(300);
            randomResult = random.nextInt(randomLimit);
        } while (randomResult % 21 != 0);
        return randomResult;
    }
}
  • 生成Future<T>對(duì)象
List<Future<Integer>> futureResults = new ArrayList<>();
ExecutorService executorService = Executors.newFixedThreadPool(5);
for (int i = 0; i < 10; i++) {
    futureResults.add(executorService.submit(randomDataCallable));
}
  • 獲取結(jié)果
int countTimes = 0;
while (futureResults.stream().filter(Future::isDone).count() != futureResults.size()) {
    Thread.currentThread().join(100);
    countTimes++;
    System.out.print("等待異步任務(wù)結(jié)果" + countTimes);
}

futureResults.forEach(futureResult->{
    try {
        System.out.println(futureResult.get());
    } catch (InterruptedException e) {
        e.printStackTrace();
    } catch (ExecutionException e) {
        e.printStackTrace();
    }
});

參考資料

  • Java核心技術(shù)(卷1)基礎(chǔ)知識(shí)
  • Java編程思想
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請(qǐng)結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

友情鏈接更多精彩內(nèi)容