线程池该怎么去理解学习(学习笔记)

如果是在Java中,可以使用UC并发编程包中的ThreadPoolExecutor来实现非常灵活地自定义线程池。

 ThreadPoolExecutor中源码所提供的需要的参数

线程池该怎么去理解学习(学习笔记)_第1张图片

线程池的参数解释


corePoolSize(核心线程数=>正式员工数):正常情况下,我们的系统应该能同时工作的线程数(随时就绪的状态)
maximumPoolSize(最大线程数=>哪怕任务再多,你也最多招这些人):极限情况下,我们的线程池最多有多少个线程?
keepAliveTime(空闲线程存活时间):非核心线程在没有任务的情况下,过多久要删除(理解为开除临时工),从而释放无用的线程资源。
TimeUnit unit(空闲线程存活时间的单位):分钟、秒
workQueue(工作队列:用于存放给线程执行的任务,存在一个队列的长度(一定要设置,不要说队列长度无限,因为也会占用资源
threadFactory(线程工冂):控制每个线程的生成、线程的属性(比如线程名)
RejectedExecutionHandler(拒绝策略):任务队列满的时候,我们采取什么措施,比如抛异常、不抛

线程池实现的流程

一开始没有任何线程,也没有任务

 

线程池该怎么去理解学习(学习笔记)_第2张图片

 后来来了任务,假设发现我们的员工还没有达到正式员工数(corePoolSize=2),来一个员工直接处理这个任务

 

线程池该怎么去理解学习(学习笔记)_第3张图片

第三和第四个任务来了,但是我们正式员工数已经满了(当前线程数=corePoolSize=2),任务放到队列(最大长度workQueue..size是2)里等待,而不是再加新员工。

 

线程池该怎么去理解学习(学习笔记)_第4张图片

又来了一个任务,但是我们的任务队列已经满了(当前线程数>corePoolSize=2,已有任务数=最大长度

workQueue.size=2),新增线程(maximumPoolSize=4)来处理新任务,而不是丢弃任务

线程池该怎么去理解学习(学习笔记)_第5张图片

已经到了任务7,但是我们的任务队列已经满了、临时工也招满了(当前线程数=maximumPoolSize=4,任务数=最大长度workQueue.size=2),调用RejectedExecutionHandler拒绝策略来处理多余的任务。

线程池该怎么去理解学习(学习笔记)_第6张图片

 具体实现的代码例子

@Configuration
public class ThreadPoolExecutorConfig {
   @Bean
    public ThreadPoolExecutor threadPoolExecutor(){
//       自定义工厂类
       ThreadFactory threadFactory=new ThreadFactory() {
           private int count=1;
           @Override
           public Thread newThread(@NotNull Runnable r) {
               Thread tread=new Thread(r);
               tread.setName("线程"+count);
               count++;
               return tread;
           }
       };
       ThreadPoolExecutor threadPoolExecutor =new ThreadPoolExecutor(2,4,
               100,TimeUnit.SECONDS,new ArrayBlockingQueue<>(4),threadFactory);
       return threadPoolExecutor;
   }

}

 

 @Resource
    private ThreadPoolExecutor threadPoolExecutor;
    @GetMapping("/add")
    public void add(String name){
        CompletableFuture.runAsync(()->{
            System.out.println("任务执行中:"+name+",执行人:"+Thread.currentThread().getName());
            try {
//                睡个600秒方便我们查看实现线程池的实现过程
                Thread.sleep(600000);
            } catch (InterruptedException e) {
                throw new RuntimeException(e);
            }

        },threadPoolExecutor);

    }
    @GetMapping("/get")
    public String get(){
        Map map=new HashMap<>();
        int size = threadPoolExecutor.getQueue().size();
        map.put("队列长度",size);
        long taskCount = threadPoolExecutor.getTaskCount();
        map.put("任务总数",taskCount);
        int activeCount = threadPoolExecutor.getActiveCount();
        map.put("正在工作的线程数",activeCount);
        long completedTaskCount = threadPoolExecutor.getCompletedTaskCount();
        map.put("已经完成的任务数",completedTaskCount);

        return JSONUtil.toJsonStr(map);
    }
}

这里的代码实现是已经有写好的后端服务才能使用,如果没有请自行写一个程序入口

你可能感兴趣的:(学习,笔记)