线程池带来的好处:
- 降低资源消耗
- 提高响应速度
- 提高线程的可管理性
线程池组件:
- 核心线程池
- 工作队列
线程池的主要处理流程: - 判断核心线程池里的线程是否都在执行任务.如果不是,创建一个新的工作线程来执行任务.如果都在执行任务,则进入下个流程.
- 判断工作队列是否已满.如果没满,则将新提交的任务存储在工作队列.如果满了,进入下个流程.
-
判断线程池的线程都处于工作状态,如果没有,则创建一个新的工作线程来执行.如果满了,交给饱和策略来处理这个任务.
lADPAuoR6mz2cfHND4DNC6A_2976_3968.jpg_620x10000q90g.jpg
ThreadPoolExecutor执行execute方法分下面4中情况:
- 如果当前运行的线程少于corePoolSize,则创建新线程来执行任务(需要获取全局锁).
- 如果运行的线程等于或多于corePoolSize,则将任务加入BlokingQueue.
- 如果无法将任务加入BlockingQueue(队列已满),则创建新的线程来处理任务(需要获取全局锁)
- 如果创建的新线程使当前运行的线程超出maximumPoolSize,任务将被拒绝,并调用RejectExecutionHandler.rejectExecution()
- 采用以上设计思路,是为了在执行execute()时,尽可能避免获取全局锁.在线程池预热完成后,几乎所有的execute都执行步骤2.
工作线程:线程池创建线程时,会将线程封装成工作线程Worker,Worker执行完任务后,会循环获取工作队列里的任务来执行.
线程池的使用
new ThreadPoolExecutor(corePoolSize, maximumPoolSize, keepAliveTime, unit, workQueue, handler)
//corePoolSize:线程池的基本大小
//runnableTaskQueue:任务队列,用于保存等待执行的阻塞队列
//1. ArrayBlockingQueue
//2. LinkedBlockingQueue
//3. SynchronousQueue
//4. PriorityBlockingQueue
//maximumPoolSize:线程池最大数量
//ThreadFactory:用于设置创建线程的工厂,可以给线程名字.
//RejectExecutionHandler(饱和策略)
//1. AbortPolicy:默认策略,直接抛出异常
//2. CallerRunsPolicy:只用调用者所在线程来运行任务.
//3. DiscardOldestPolicy:丢弃队列里最近的一个任务,并执行当前任务
//4. DiscardPolicy:不处理,不丢弃
//5. 自定义
// keepAliveTime:线程活动保持事件
//TimeUnit:线程活动保持时间的单位
向线程池提交任务
execute()用于提交不需要返回值的任务
submit() 提交需要返回值的任务