前言
线程池不推荐使用Executors创建,而是推荐使用ThreadPoolExecutor创建。 Executors返回的线程池对象的弊端如下: 1)FixedThreadPool和SingleThreadPool: 允许的请求队列长度为Integer.MAX_VALUE,可能会堆积大量的请求,从而导致OOM。 2)CachedThreadPool: 允许的创建线程数量为Integer.MAX_VALUE,可能会创建大量的线程,从而导致OOM。 3)ScheduledThreadPool: 允许的请求队列长度为Integer.MAX_VALUE,可能会堆积大量的请求,从而导致OOM。
参数解读
源码截图
ThreadPoolExecutor构造方法 ·corePoolSize:保留在池中的线??程数 ·maximumPoolSize:池中允许的最大线程数 ·keepAliveTime:当线程数大于核心时,多余的空闲线程在终止前等待新任务的最长时间 ·unit:keepAliveTime参数的时间单位 ·workQueue:用于在执行任务之前保存任务的队列 ·threadFactory:执行器创建新线程时使用的工厂 ·handler:由于达到线程边界和队列容量而阻塞执行时使用的处理程序
代码示例
ThreadPoolExecutor executor = new ThreadPoolExecutor(50, 100, 5L, TimeUnit.SECONDS, new LinkedBlockingQueue<>(100), Executors.defaultThreadFactory(), new ThreadPoolExecutor.AbortPolicy());
executor.execute(() -> {
});
代码示例中,创建了一个,核心线程数50,最大线程数100,队列大小100的线程池。
线程池大小变化规则
以示例代码为例子: 线程池刚刚创建的时候,是没有活跃或空闲线程的; 当有任务创建时,线程池会同步创建线程,直至达到50个线程(corePoolSize); 多余的任务会在队列中保存,直至大小等于100的队列被塞满(workQueue); 队列已满的情况下,线程池会进行扩容,直至达到最大线程数100(maximumPoolSize); 若线程池队列已满、已达到最大线程数且没有空闲线程,后续的任务将被拒绝,并抛出异常; 当任务都执行完毕后,且超过我们设置的线程超时时间(keepAliveTime),多余的空闲线程将被终止,线程池大小会保持在50(corePoolSize);
参考
OpenJDK17 阿里巴巴Java开发手册:https://github.com/alibaba/p3c
|