线程池ThreadPoolExecutor

Posted by XBeats on 2016-11-11

线程池.png

ThreadPoolExecutor的构造方法:

public ThreadPoolExecutor(int corePoolSize,  
                          int maximumPoolSize,  
                          long keepAliveTime,  
                          TimeUnit unit,  
                          BlockingQueue<Runnable> workQueue,  
                          ThreadFactory threadFactory,  
                          RejectedExecutionHandler handler)  

###说明 - corePoolSize: 线程池维护线程的最少数量
- maximumPoolSize:线程池维护线程的最大数量 - keepAliveTime: 线程池维护线程所允许的空闲时间 - unit: 线程池维护线程所允许的空闲时间的单位 - workQueue: 线程池所使用的缓冲队列 - handler: 线程池对拒绝任务的处理策略

###逻辑 1. 当池子线程数量小于corePoolSize就新建线程,并处理请求

  1. 当池子大小等于corePoolSize,就会将请求放入workQueue中,等池子里的线程空闲了,就去从workQueue中取任务并处理

  2. 当workQueue放不下新入的任务时,新建线程入池,并处理请求,如果池子大小撑到了maximumPoolSize就用RejectedExecutionHandler来做拒绝处理

  3. 另外,当池子的线程数大于corePoolSize的时候,多余的线程会等待keepAliveTime长的时间,如果无请求可处理就自行销毁

###理解 一个任务通过 execute(Runnable)方法被添加到线程池,任务就是一个 Runnable类型的对象,任务的执行方法就是Runnable类型对象的run()方法。

###参数 unit 可选的参数为java.util.concurrent.TimeUnit中的几个静态属性: - NANOSECONDS - MICROSECONDS - MILLISECONDS 毫秒 - SECONDS 秒

workQueue 常用的是:java.util.concurrent.ArrayBlockingQueue
- SynchronousQueue 直接提交,它将任务直接提交给线程而不保持它们。 - LinkedBlockingQueue 无界队列,将导致在所有 corePoolSize 线程都忙的情况下将新任务加入队列。 - ArrayBlockingQueue 有界队列,有助于防止资源耗尽,但是可能较难调整和控制。 …

handler 有四个选择: - ThreadPoolExecutor.AbortPolicy()
抛出java.util.concurrent.RejectedExecutionException异常   - ThreadPoolExecutor.CallerRunsPolicy()
当抛出RejectedExecutionException异常时,会调用rejectedExecution方法 (如果主线程没有关闭,则主线程调用run方法,源码如下

public void rejectedExecution(Runnable r, ThreadPoolExecutor e) {            
         if (!e.isShutdown()) {                
                 r.run();            
         }
        }
)

  - ThreadPoolExecutor.DiscardOldestPolicy()
抛弃旧的任务   - ThreadPoolExecutor.DiscardPolicy()
抛弃当前的任务