文章目录

  • 叙述
  • 线程池的实现原理
  • 线程池的机制
  • ThreadPoolExecutor


Java中的线程池是运用场景最多的并发框架,几乎所有需要异步或并发执行任务的程序都可以使用线程池。

叙述

线程池的实现原理

当向线程池提交一个任务之后,线程池是如何处理这个任务的呢?我们来看一下线程池的主要处理流程。

java中线程池怎么设定 java中线程池是如何实现的_多线程

  1. 线程池判断核心线程池里的线程是否都在执行任务。如果不是,则创建一个新的工作线程来执行任务。如果核心线程池里的线程都在执行任务,则进入下一个流程。
  2. 线程池判断工作队列是否已经满。如果工作队列没有满,则将新提交的任务存储在这个工作队列里。如果工作队列满了,则进入下一个流程。
  3. 线程池判断线程池的线程是否都处于工作状态。如果没有,则创建一个新的工作线程来执行任务。如果已经满了,则交给饱和策略来处理这个任务。

线程池的机制

  1. 如果正在运行的线程数 < coreSize,马上创建线程执行该task,不排队等待;
  2. 如果正在运行的线程数 >= coreSize,把该task放入阻塞队列;
  3. 如果队列已满 && 正在运行的线程数 < maximumPoolSize,创建新的线程执行该task;
  4. 如果队列已满 && 正在运行的线程数 >= maximumPoolSize,线程池调用handler的reject方法拒绝本次提交。

从worker线程自己的角度来看,当worker的task执行结束之后,循环从阻塞队列中取出任务执行。

java中线程池怎么设定 java中线程池是如何实现的_工作队列_02

ThreadPoolExecutor

创建线程池主要是ThreadPoolExecutor类来完成,ThreadPoolExecutor的有许多重载的构造方法,通过参数最多的构造方法来理解创建线程池有哪些需要配置的参数。
ThreadPoolExecutor的构造方法:

ThreadPoolExecutor(int corePoolSize,
                              int maximumPoolSize,
                              long keepAliveTime,
                              TimeUnit unit,
                              BlockingQueue<Runnable> workQueue,
                              ThreadFactory threadFactory,
                              RejectedExecutionHandler handler)
  1. corePoolSize:表示核心线程池的大小。
  2. maximumPoolSize:表示线程池能创建线程的最大个数。
  3. keepAliveTime:空闲线程存活时间。
  4. unit:时间单位。为keepAliveTime指定时间单位。
  5. workQueue:阻塞队列。用于保存任务的阻塞队列。可以使用ArrayBlockingQueue, LinkedBlockingQueue, SynchronousQueue,PriorityBlockingQueue。
  6. threadFactory:创建线程的工程类。
  7. handler:饱和策略。当线程池的阻塞队列已满和指定的线程都已经开启,说明当前线程池已经处于饱和状态了,那么就需要采用一种策略来处理这种情况。采用的策略有这几种:
  • AbortPolicy: 直接拒绝所提交的任务,并抛出RejectedExecutionException异常;
  • CallerRunsPolicy:只用调用者所在的线程来执行任务;
  • DiscardPolicy:不处理直接丢弃掉任务;
  • DiscardOldestPolicy:丢弃掉阻塞队列中存放时间最久的任务,执行当前任务

感谢您的阅读~~