线程池的三种队列:SynchronousQueue、LinkedBlockingQueue 和ArrayBlockingQueue

使用方法:

SynchronousQueue

private static ExecutorService cachedThreadPool = new ThreadPoolExecutor(4, 
Runtime.getRuntime().availableProcessors() * 2, 
0, 
TimeUnit.MILLISECONDS, 
new SynchronousQueue<>(), 
r -> new Thread(r, "ThreadTest"),
new ThreadPoolExecutor.AbortPolicy());

参数分别为:
1.corePoolSize:线程池中的常驻核心线程数

2.maximumPoolSize:线程池能够容纳同时执行的最大线程数,此值必须大于1,Runtime.getRuntime().availableProcessors() * 2 这个意思是处理器核心数*2

3.keepAliveTime:多余的空闲线程的存活时间,当空闲时间达到keepAliveTime值时,多余空闲线程会被销毁直到只剩下corePoolSize个线程为止。

4.unit:keepAliveTime的单位

5.workQueue:任务队列,被提交但尚未执行的任务

6.threadFactory:表示生成线程池中工作线程的线程工厂,用于创建线程一般用默认的即可

7.handIer:拒绝策略,表示当队列满了并且工作线程大于等于线程池的最大线程数(maximumPoolSize)

说明:

SynchronousQueue没有容量,是无缓存等待队列,是一个不存储元素的阻塞队列,会直接将任务交给消费者,必须等待队列中的添加元素被消费后才能继续添加新的元素。

拥有公平(FIFO)和非公平(LIFO)策略,非公平策略会导致一些数据永远无法被消费的情况

使用SynchronousQueue阻塞队列一般要求maximumPoolSizes为无界(Integer.MAX_VALUE),避免线程拒绝执行操作。

LinkBlockingQueue

private static ExecutorService cachedThreadPool = new ThreadPoolExecutor(4,
Runtime.getRuntime().availableProcessors() * 2, 
0, 
TimeUnit.MILLISECONDS, 
new LinkedBlockingQueue<>(), 
r -> new Thread(r, "ThreadTest"));

说明:

LinkedBlockingQueue是一个无界缓存等待队列。当前执行的线程数量达到corePoolSize的数量时,剩余的元素会在阻塞队列里等待。(所以在使用此阻塞队列时,maximumPoolSize就相当于无效了),每个线程完全独立于其他线程。生产者和消费者使用独立的锁来控制数据的同步,即在高并发的情况下可以并行操作队列中的数据。

注:

这个队列需要注意的是,虽然通常称其为一个无界队列,但是可以人为指定队列大小,而且由于其用于记录队列大小的参数是int类型字段,所以通常意义上的无界其实就是队列长度为Integer.MAX_VALUE,且在不指定队列大小的情况下,也会默认队列大小为Integer.MAX_VALUE,等同于如下:

private static ExecutorService cachedThreadPool = new ThreadPoolExecutor(4, 
Runtime.getRuntime().availableProcessors() * 2, 
0, 
TimeUnit.MILLISECONDS, 
new LinkedBlockingQueue<>(Integer.MAX_VALUE), 
r -> new Thread(r, "ThreadTest"));

ArrayBlockIngQueue

private static ExecutorService cachedThreadPool = new ThreadPoolExecutor(4, 
Runtime.getRuntime().availableProcessors() * 2, 
0, 
TimeUnit.MILLISECONDS, 
new ArrayBlockingQueue<>(32), 
r -> new Thread(r, "ThreadTest"));

说明:

ArrayBlockingQueue是一个有界缓存等待队列,可以指定缓存队列的大小,当正在执行的线程数等于corePoolSize时,多余的元素缓存在ArrayBlockingQueue队列中等待有空闲的线程时继续执行,当ArrayBlockingQueue已满时,加入ArrayBlockingQueue失败,会开启新的线程去执行,当线程数达到最大的maximumPoolSize时,再有新的元素尝试加入ArrayBlockingQueue时会报错。

    原文作者:某科学的南条
    原文地址: https://blog.csdn.net/lqq404270201/article/details/109333441
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞