说说Java的线程池
文章目录
- 说说Java的线程池
- 为什么要使用线程池
- ThreadPoolExecutor提供的构造方法
-
- 线程池处理流程
为什么要使用线程池
- 创建/销毁线程需要消耗系统资源,线程池可以复用已创建的线程
- 控制并发的数量,并发数量过多,可能会导致资源消耗过多,从而曹诚服务器崩溃
- 可以对线程做统一管理
ThreadPoolExecutor提供的构造方法
五个参数的构造参数
public ThreadPoolExecutor(int corePoolSize, int maximumPoolSize, long keepAliveTime,TimeUtil unit, BlockingQueue<Runnable> workQueue)
六个参数的构造参数(一)
public ThreadPoolExecutor(int corePoolSize, int maximumPoolSize, long keepAliveTime, TimeUnit unit, BlockingQueue<Runnable> workQueue, ThreadFactory threadFactory)
六个参数的构造参数(二)
public ThreadPoolExecutor(int corePoolSize, int maximumPoolSize, long keepAliveTime, TimeUnit unit, BlockingQueue<Runnable> workQueue, RejectedExecutionHandler handler)
七个参数的构造参数
public ThreadPoolExecutor(int corePoolSize,
int maximumPoolSize,
long keepAliveTime,
TimeUnit unit,
BlockingQueue<Runnable> workQueue,
ThreadFactory threadFactory,
RejectedExecutionHandler handler)
解析
-
int corePoolSize : 该线程池中核心线程数最大值
核⼼线程:线程池中有两类线程,核⼼线程和⾮核⼼线程。核⼼线程默 认情况下会⼀直存在于线程池中,即使这个核⼼线程什么都不⼲(铁饭 碗),⽽⾮核⼼线程如果⻓时间的闲置
,就会被销毁(临时⼯)。
-
int maximumPoolSize : 该线程池中线程总数最大值
该值等于核⼼线程数量 + ⾮核⼼线程数量。
-
long keepAliveTime: 非核心线程闲置超时时长
该值等于核⼼线程数量 + ⾮核⼼线程数量。
-
TimeUnit unit: keepAliveTime 的单位
TimeUnit是一个枚举类型,包括以下属性:
NANOSECONDS : 1微毫秒 = 1微秒 / 1000 MICROSECONDS : 1微秒 =
1毫秒 / 1000 MILLISECONDS : 1毫秒 = 1秒 /1000 SECONDS : 秒
MINUTES : 分 HOURS : ⼩时 DAYS : 天
-
BlockingQueue workQueue: 阻塞队列,维护着等待执行的Runnable任务
- LinkedBlockingQueue 链式阻塞队列,底层数据结构是链表,默认⼤⼩是 Integer.MAX_VALUE , 也可以指定⼤⼩。
- ArrayBlockingQueue 数组阻塞队列,底层数据结构是数组,需要指定队列的⼤⼩。
- SynchronousQueue 同步队列,内部容量为0,每个put操作必须等待⼀个take操作,反之亦 然。
- DelayQueue 延迟队列,该队列中的元素只有当其指定的延迟时间到了,才能够从队列 中获取到该元素 。
-
ThreadFactory threadFactory:创建线程的⼯⼚ ,⽤于批量创建线程,统⼀在创建线程时设置⼀些参数,如是 否守护线程、线程的优先级等。如果不指定,会新建⼀个默认的线程⼯⼚。
ThreadFactory threadFactory = new ThreadFactory() {
@Override
public Thread newThread(Runnable r) {
Thread t = new Thread(r);
return t;
}
};
-
RejectedExecutionHandler handler 拒绝策略,当线程数量大于最大线程数就会采用拒绝处理策略,四种拒绝处理策略为:
- ThreadPoolExecutor.AbortPolicy:默认拒绝处理策略,丢弃任务并抛 出RejectedExecutionException异常。
- ThreadPoolExecutor.DiscardPolicy:丢弃新来的任务,但是不抛出异 常。
- ThreadPoolExecutor.DiscardOldestPolicy:丢弃队列头部(最旧的) 的任务,然后重新尝试执⾏程序(如果再次失败,重复此过程)。
- ThreadPoolExecutor.CallerRunsPolicy:由调⽤线程处理该任务
线程池处理流程
- 线程总数量 < corePoolSize,⽆论线程是否空闲,都会新建⼀个核⼼线程执⾏ 任务(让核⼼线程数量快速达到corePoolSize,在核⼼线程数量 < corePoolSize时)。注意,这⼀步需要获得全局锁。
- 线程总数量 >= corePoolSize时,新来的线程任务会进⼊任务队列中等待,然 后空闲的核⼼线程会依次去缓存队列中取任务来执⾏(体现了线程复⽤)。
- 当缓存队列满了,说明这个时候任务已经多到爆棚,需要⼀些“临时⼯”来执⾏ 这些任务了。于是会创建⾮核⼼线程去执⾏这个任务。注意,这⼀步需要获得 全局锁。
- 缓存队列满了, 且总线程数达到了maximumPoolSize,则会采取上⾯提到的 拒绝策略进⾏处理。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)