0

12.线程池源码及优化指南

 3 years ago
source link: http://sunliangliang.com/?p=49
Go to the source link to view the article. You can view the picture content, updated content and better typesetting reading experience. If the link is broken, please click the button below to view the snapshot at that time.

12.线程池源码及优化指南

发表于 2021-03-18 | 分类于 并发编程 | 0 | 阅读次数 25

线程池的使用及源码解析

  • 线程池的分类以及核心参数
  • 线程池的提交流程以及执行流程

1.线程池

1.1.分类

线程池分为很多种

  • fixed线程池:维护固定数量线程的线程池。

通过AtomicInteger ctl(32位)来判定线程池状态,以及线程内的线程数量。

1.2.核心参数

  • corePoolSize:核心线程数,线程池里有多少个线程
  • maxPoolSize: 线程池中最多有多少个线程数
  • keepAliveTime+TimeUnit: 超过corePoolSize的线程存活时间,即超出部分的线程在空闲该时间后会自动消亡
  • workQueue:线程池中的等待队列
  • threadFactory:创建线程的线程功能
  • RejectedHandler:线程拒绝策略。可以自定义

1.3.任务提交到线程池执行流程

  • 小于corePoolSize,创建线程并放入线程池
  • 大于等于corePoolSize,加入队列排队,排队候若线程池已关闭,则需要将刚加入的任务出队。
  • 队列已满,且无法创建新的线程,直接走reject策略
  • 线程队列中存储的是Worker(AQS),
int c = ctl.get();
if (workerCountOf(c) < corePoolSize) {
    if (addWorker(command, true))
        return;
    c = ctl.get();
}
if (isRunning(c) && workQueue.offer(command)) {
    int recheck = ctl.get();
    if (! isRunning(recheck) && remove(command))
        reject(command);
    else if (workerCountOf(recheck) == 0)
        addWorker(null, false);
}
else if (!addWorker(command, false))
    reject(command);

2.线程池整体执行过程

2.1.执行概要

  • 1.提交任务:
    • 线程释放执行:基于一个AtomicInteger的变量ctl(32位),前3位表示线程状态,后29位表示线程数量
  • 2.提交到线程池:
    • 线程池(hashSet): 若当前线程小于corePoolSize,则将任务封装成一个Worker(AQS)作为工作线程入池

2.2.执行细节

坚持有质量的创作,您的支持将支持我继续创作!

About Joyk


Aggregate valuable and interesting links.
Joyk means Joy of geeK