Java面试必问之线程池的创建使用、线程池的核心参数、线程池的底层工作原理

一、前言

大家在面试过程中,必不可少的问题是线程池,小编也是在面试中被问啥傻了,JUC就了解的不多。加上做系统时,很少遇到,自己也是一知半解,最近看了尚硅谷阳哥的课,恍然大悟,特写此文章记录一下!如果还不了解线程池的小伙伴,一定要认真看完,你会有收获的哈!!

二、线程池创建使用

答:使用Executors看一下源码是有好多个,经常用的也就三个,今天就展示靠上的五种。

java 复制代码
//创建一个定长线程池,超出的线程会在队列中等待
ExecutorService executorService = Executors.newFixedThreadPool(5);
//创建一个单线程化的线程池,它只会用唯一的工作线程来执行任务,
ExecutorService executorService1 = Executors.newSingleThreadExecutor();
//创建一个可缓存线程池,可以自动扩容,扩容大小为int最大值,因为太大可以直接理解为无限大
ExecutorService executorService2 = Executors.newCachedThreadPool();
//创建一个定长线程池,该线程池可以安排命令在给定延迟后运行,或定期执行。
ScheduledExecutorService scheduledExecutorService = Executors.newScheduledThreadPool(5);
//1.8新增-创建一个带并行级别的线程池,并行级别决定了同一时刻最多有多少个线程在执行,不传参数默认为CPU个数
// Runtime.getRuntime().availableProcessors()查看本机CPU个数
ExecutorService executorService3 = Executors.newWorkStealingPool();

三、线程池的核心参数

java 复制代码
//创建线程池,底层代码
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.corePoolSize = corePoolSize;
    this.maximumPoolSize = maximumPoolSize;
    this.workQueue = workQueue;
    this.keepAliveTime = unit.toNanos(keepAliveTime);
    this.threadFactory = threadFactory;
    this.handler = handler;
}

1. corePoolSize:线程池中的核心线程数,核心线程会一直存在,即使没有任务执行。 2. maximumPoolSize:线程池能够容纳同时执行的最大线程数,此值必须大于等于1 3. keepAliveTime:当线程数大于核心数时,这是多余空闲线程在终止前等待新任务的最长时间。(意思就是本来核心线程三个,已占满,扩展到最大线程数到5,解决完后没有线程任务了,这时设置一个时间,过了这个时间被扩展的2个非核心线程会被回收) 4. unit:keepAliveTime的时间单位。 5. workQueue:任务队列,被提交但尚未被执行的任务,相当于去饭店吃饭,餐桌满了,要在外边排队(阻塞队列) 6. threadFactory:表示生成线程池中工作线程的线程工厂,用于创建线程一般用默认的即可。 7. handler:拒绝策略,表示当队列满了并且工作线程大于等于线程池的最大线程数。

四、线程池的底层工作原理

- 主要处理流程图(来源百度) - 底层工作原理图(来源尚硅谷阳哥) - 流程梳理

1. 在创建了线程池后,等待提交过来的任务请求。 2. 当调用execute()方法添加一个请求任务时,线程池会做如下判断: 2.1 如果正在运行的线程数量小于corePoolSize,那么马上创建线程运行这个任务; 2.2 如果正在运行的线程数量大于或等于corePoolSize,那么将这个任务放入队列; 2.3 如果这时候队列满了且正在运行的线程数量还小于maximumPoolSize,那么还是要创建非核心线程立刻运行这个任务; 2.4 如果队列满了且正在运行的线程数量大于或等于maximumPoolSize,那么线程池会启动饱和拒绝策略来执行。 3.当一个线程完成任务时,它会从队列中取下一个任务来执行。 4.当一个线程无事可做超过一定的时间(keepAliveTime)时,线程池会判断: 如果当前运行的线程数大于corePoolSize,那么这个线程就被停掉;所以线程池的所有任务完成后它最终会收缩到corePoolSize 的大小。

五、总结

这样就理解很透彻了,希望面试的时候能够帮助到你!

建了一个IT技术交流群,欢迎大家加入,一起学习!过期私信我拉你们进哈!

相关推荐
xcl092511 小时前
北京24小时自助健身房系统软件开发实战:从架构到部署全流程指南
java·spring boot·架构
一 乐13 小时前
动漫书销售商城|基于springboot + vue动漫书销售商城(源码+数据库+文档)
java·数据库·vue.js·spring boot·毕业设计
卓怡学长13 小时前
w214基于jsp知道特产网
java·intellij-idea
步行cgn14 小时前
Spring 注解使用详解
java·spring
一条小小yu14 小时前
Spring IoC的理解
java·后端·spring
落魄实习生14 小时前
Agent Scope Java 2.x 系列【7】工具使用
java·开发语言·ai
旺仔学长 哈哈14 小时前
springboot钓鱼爱好者交流平台APP设计与实现
java·spring boot·mysql·充电桩管理系统
自强的小白16 小时前
核心功能(Service接口)
java·mybatis
乌暮17 小时前
深入理解 Java 泛型:把「万能盒子」用对、用稳
java·开发语言·后端·学习