线程池ExecutorService

1.线程池创建方式

1)通过Executors创建线程池

import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

public class ExecutorServiceDemo {
    static ExecutorService executorService = Executors.newFixedThreadPool(10);

    public static void main(String[] args) {

        executorService.execute(new RunableDemo());
    }
}

2)原生方式实现

此处注意LinkedBlockingDeque的默认大小是Integer.MAX_VALUE,在使用是要注意给初始化大小,否则可能会导致内存占满的问题

import java.util.concurrent.*;

public class ExecutorServiceDemo {

    public static void main(String[] args) {
        ThreadPoolExecutor threadPoolExecutor =
                new ThreadPoolExecutor(10, 20, 30, TimeUnit.SECONDS, new LinkedBlockingDeque<>(), Executors.defaultThreadFactory(), new ThreadPoolExecutor.AbortPolicy());
        threadPoolExecutor.allowCoreThreadTimeOut(true);
    }
}

ThreadPoolExecutor继承了AbstractExecutorService类,而AbstractExecutorService类实现了ExecutorService接口。其本质与Executors创建出的线程池返回的是同一个对象ExecutorService

 通过ThreadPoolExecutor创建线程池有七大参数

 

(1)corePoolSize:线程池保持的线程数量,即使这些线程是空闲状态,也不会被释放,除非设置了
                          allowCoreThreadTimeOut参数

threadPoolExecutor.allowCoreThreadTimeOut(true);

(2)maximumPoolSize:线程池允许存在的最大线程数量

(3)keepAliveTime:存活时间,当前线程数量大于核心线程数时,如果非核心线程在此时间间隔中                                 未接收处理任务时,将会被释放

(4)unit:时间单位

 

(5)workQueue:阻塞队列,当任务较多,当前线程池线程不能全部处理时,将任务放入队中,

                                当线程池中有空闲线程时,再从队列中取出任务执行

 

(6)threadFactory:线程创建工厂

 

(7)handler:拒绝策略,用于处理线程全部被占用且队列存满后对再提交任务的处理

 

2.线程执行流程

(1)线程池创建,准备好core数量的核心线程,准备接受任务

(2)新任务需要处理,空闲的核心线程处理任务

        1.当核心线程全部被占用时,就将提交的任务存放到阻塞队列中,空闲的核心线程会到阻塞               队列中去获取任务执行

        2.当提交的任务较多,核心线程数都不处于空闲状态,且阻塞队列也已经被存满了,线程池               开始创建新的线程去执行任务,但是会保证线程池中的线程数不会大于maximumPoolSize

        3.如果任务多,线程池已经达到了最大线程数,且都在处理任务,则其他提交的任务就会被               执行拒绝策略

(3)当非核心线程在keepAliveTime时间间隔内未接受到任务时,则非核心线程会被释放

3.场景分析

eg:如果一个线程池的core数量是7,maximumPoolSize是20,workQueue为50,如果有100个任务并发提交到线程池,线程池应该是怎么分配

此时有7个任务会被核心线程执行,这时其他50个任务会被存放到workQueue中,这时,核心线程全部被占用且阻塞队列已经存满,线程池会新开线程去处理剩下的43个任务,但是线程池最多只能有20个线程,而7个是核心线程,这时最多只能开13个线程去执行剩下的任务,这样就还会有30个线程会被执行拒绝策略。

4.Executors可创建的4种线程池

 public static ExecutorService newFixedThreadPool(int nThreads) {
        return new ThreadPoolExecutor(nThreads, nThreads,
                                      0L, TimeUnit.MILLISECONDS,
                                      new LinkedBlockingQueue<Runnable>());
}
public static ExecutorService newCachedThreadPool() {
        return new ThreadPoolExecutor(0, Integer.MAX_VALUE,
                                      60L, TimeUnit.SECONDS,
                                      new SynchronousQueue<Runnable>());
}
public static ScheduledExecutorService newScheduledThreadPool(int corePoolSize) {
        return new ScheduledThreadPoolExecutor(corePoolSize);
}
public static ExecutorService newSingleThreadExecutor() {
        return new FinalizableDelegatedExecutorService
            (new ThreadPoolExecutor(1, 1,
                                    0L, TimeUnit.MILLISECONDS,
                                    new LinkedBlockingQueue<Runnable>()));
}
 public static ExecutorService newWorkStealingPool() {
        return new ForkJoinPool
            (Runtime.getRuntime().availableProcessors(),
             ForkJoinPool.defaultForkJoinWorkerThreadFactory,
             null, true);
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

bigbear776

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值