ThreadPoolExecutor创建线程池
一、前言
ThreadPoolExecutor是Java中用于管理线程池的类,它提供了一个灵活且可配置的线程池,可以有效地执行并管理多个任务。使用ThreadPoolExecutor可以实现线程的复用、线程池大小的控制、任务调度和异常处理等功能。
二、相关介绍
1. 构造函数定义
当使用new关键字去创建ThreadPoolExecutor类型的对象时,相关的构造函数定义如下:
public ThreadPoolExecutor(int corePoolSize,
int maximumPoolSize,
long keepAliveTime,
TimeUnit unit,
BlockingQueue<Runnable> workQueue,
ThreadFactory threadFactory,
RejectedExecutionHandler handler) {
if (corePoolSize < 0 ||
maximumPoolSize <= 0 ||
maximumPoolSize < corePoolSize ||
keepAliveTime < 0)
throw new IllegalArgumentException();
if (workQueue == null || threadFactory == null || handler == null)
throw new NullPointerException();
this.acc = System.getSecurityManager() == null ?
null :
AccessController.getContext();
this.corePoolSize = corePoolSize;
this.maximumPoolSize = maximumPoolSize;
this.workQueue = workQueue;
this.keepAliveTime = unit.toNanos(keepAliveTime);
this.threadFactory = threadFactory;
this.handler = handler;
}
2. 构造函数参数解读
corePoolSize(核心线程数):- 必须大于或等于零
- 定义线程池的基本大小,即在没有任务执行时线程池的大小。
- 核心线程会一直存活,即使没有任务需要执行。
- 当任务数量超过核心线程数时,线程池会创建新的线程来处理任务,直到达到最大线程数。
- 如果调用了线程池的
prestartCoreThread()方法,核心线程会提前启动。
maximumPoolSize(最大线程数):- 必须大于零,且大于或等于核心线程数
- 定义线程池允许创建的最大线程数。
- 当任务数量超过核心线程数时,线程池会创建新的线程来处理任务,直到达到最大线程数。
- 如果任务数量继续增加,而最大线程数已经达到,那么新的任务会被放入等待队列中等待执行。
什么是等待队列?
等待队列是在线程池中用于存储无法立即执行的任务的队列。当线程池中的线程数已达到最大线程数时,新提交的任务会被放入等待队列中等待执行。等待队列可以采用不同的实现,如
ArrayBlockingQueue、LinkedBlockingQueue、SynchronousQueue等。如果等待队列已满,并且线程池中的线程数已达到最大线程数,那么线程池会根据预定义的拒绝策略来处理新提交的任务。
keepAliveTime(线程空闲时间):- 必须大于或等于零
- 当线程池中的线程数量超过核心线程数时,多余的空闲线程的存活时间。
- 当线程处于空闲状态,并且空闲时间超过
keepAliveTime时,线程会被终止,直到线程数量等于核心线程数。
unit(时间单位):- 用于定义
keepAliveTime参数的时间单位,可以是TimeUnit.MILLISECONDS(毫秒)、TimeUnit.SECONDS(秒)等。
- 用于定义
workQueue(工作队列):- 必须非空
- 用于存储待执行任务的队列。
- 当任务数量超过核心线程数时,新的任务会被放入工作队列中等待执行。
- 工作队列采用先进先出(FIFO)的原则,即先提交的任务先执行。
ThreadPoolExecutor提供了多种实现类,如ArrayBlockingQueue、LinkedBlockingQueue、SynchronousQueue等。
threadFactory(线程工厂):- 必须非空
- 用于创建新线程的工厂。
- 可以自定义线程工厂,以便为线程设置特定的属性,如名称、优先级等。
handler(拒绝策略):- 必须非空
- 当线程池和工作队列都满了,无法执行新的任务时,拒绝策略会定义如何处理这些任务。
ThreadPoolExecutor提供了多种预定义的拒绝策略,如AbortPolicy、CallerRunsPolicy、DiscardPolicy、DiscardOldestPolicy等。Java中的
ThreadPoolExecutor类提供了哪些预定义的拒绝策略?-
AbortPolicy(默认):如果等待队列已满且线程池中的线程数已达到最大线程数,新提交的任务会立即抛出
RejectedExecutionException异常,阻止任务的执行。 -
CallerRunsPolicy:如果等待队列已满且线程池中的线程数已达到最大线程数,新提交的任务会由调用线程直接执行,而不会启动新的线程。
-
DiscardPolicy:如果等待队列已满且线程池中的线程数已达到最大线程数,新提交的任务会被默默地丢弃,不会抛出异常,也不会执行。
-
DiscardOldestPolicy:如果等待队列已满且线程池中的线程数已达到最大线程数,新提交的任务会尝试替换等待队列中最早的任务(即队头任务),然后重新提交新任务。
-
三、线程池处理流程

四、使用示例
1. 简单使用
public static void main(String[] args) {
// 创建ThreadPoolExecutor
ThreadPoolExecutor threadPoolExecutor = new ThreadPoolExecutor(5,
10, 5000,
TimeUnit.MICROSECONDS, new LinkedBlockingDeque<>(),
Executors.defaultThreadFactory(), new ThreadPoolExecutor.AbortPolicy());
// 提交任务给线程池执行
for (int i = 0; i < 20; i++) {
// 创建任务对象
Runnable task = () -> System.out.println(Thread.currentThread().getName() + ":任务执行啦");
threadPoolExecutor.execute(task);
}
// 关闭线程池
threadPoolExecutor.shutdown();
}
结果记录:
pool-1-thread-2:任务执行啦
pool-1-thread-3:任务执行啦
pool-1-thread-5:任务执行啦
pool-1-thread-1:任务执行啦
pool-1-thread-4:任务执行啦
pool-1-thread-5:任务执行啦
pool-1-thread-3:任务执行啦
pool-1-thread-2:任务执行啦
pool-1-thread-5:任务执行啦
pool-1-thread-4:任务执行啦
pool-1-thread-1:任务执行啦
pool-1-thread-1:任务执行啦
pool-1-thread-1:任务执行啦
pool-1-thread-1:任务执行啦
pool-1-thread-4:任务执行啦
pool-1-thread-4:任务执行啦
pool-1-thread-5:任务执行啦
pool-1-thread-2:任务执行啦
pool-1-thread-3:任务执行啦
pool-1-thread-1:任务执行啦
2. Spring中使用
/**
* 线程池
*
* @Author: Isabener
* @Date: 2023/5/28 11:04:58
*/
@Configuration
public class TaskPoolConfig {
@Bean(name = "passionAsyncExecutor")
public Executor taskExecutor() {
ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();
executor.setCorePoolSize(7);
executor.setMaxPoolSize(15);
executor.setQueueCapacity(50);
executor.setKeepAliveSeconds(60);
executor.setThreadNamePrefix("passion-asyns-executor-");
executor.setRejectedExecutionHandler(new ThreadPoolExecutor.CallerRunsPolicy());
return executor;
}
}
/**
* 注:该方法所在类需要被Spring所管理
*/
@Async("passionAsyncExecutor")
public void test() {
//业务逻辑
}
ThreadPoolExecutor是Java用于管理线程池的工具,它允许配置核心线程数、最大线程数、线程空闲时间等参数。当任务超出线程池容量时,任务会被放入等待队列或根据拒绝策略处理。示例展示了如何创建和使用线程池执行任务。
1587

被折叠的 条评论
为什么被折叠?



