创建线程的方式:

    a、New Thread (代表真正意义的线程) 有自己的生命周期(start)
    b、Implement Runable 只是重写了run()方法,还是要借助于New Thread() 来创建线程

一、使用线程池的目的
(1)减少系统维护线程的开销
(2)解耦、运行和创建分开
(3)线程可以复用
二、线程池的使用
线程池的分类(常用的4类)
方法名 解释
newCachedThreadPool() 创建一个根据需要创建新线程的线程池,但在可用时将重新使用以前构造的线程。
newFixedThreadPool(int nThreads) 创建一个线程池,该线程池重用固定数量的从共享无界队列中运行的线程。
newSingleThreadExecutor() 创建一个使用从无界队列运行的单个工作线程的执行程序
newScheduledThreadPool(int corePoolSize) 创建一个线程池,可以调度命令在给定的延迟之后运行,或定期执行。
三、线程池的原理

(1)核心参数 —–》ThreadPoolExecutor

public static ExecutorService newCachedThreadPool() {
    return new ThreadPoolExecutor(0, Integer.MAX_VALUE,
                                  60L, TimeUnit.SECONDS,
                                  new SynchronousQueue<Runnable>());
}

        (a)打开ThreadPoolExecutor源码

public ThreadPoolExecutor(int corePoolSize,
                          int maximumPoolSize,
                          long keepAliveTime,
                          TimeUnit unit,
                          BlockingQueue<Runnable> workQueue){
   this(corePoolSize, maximumPoolSize, keepAliveTime, unit, workQueue,
        Executors.defaultThreadFactory(), defaultHandler);
}

        其中

参数名 解释
int corePoolSize 限定线程池的基本大小
int maximumPoolSize 最大线程数量
long keepAliveTime 线程保持的活动时间
TimeUnit unit 线程保持的活动时间单位
BlockingQueue workQueue 任务阻塞队列
defaultHandler 拒绝策略

(2)状态变化

        (a)ThreadPoolExecutor源码

private static final int COUNT_BITS = Integer.SIZE - 3;
private static final int CAPACITY   = (1 << COUNT_BITS) - 1;

COUNT_BITS :一共29位,表示线程数量,剩下高3位表示状态码
CAPACITY :最大线程数 即2^29,共536870911

        (b)线程池的状态

private static final int RUNNING    = -1 << COUNT_BITS;
private static final int SHUTDOWN   =  0 << COUNT_BITS;
private static final int STOP       =  1 << COUNT_BITS;
private static final int TIDYING    =  2 << COUNT_BITS;
private static final int TERMINATED =  3 << COUNT_BITS;

        (c)线程池的状态转换图

(3)线程池的执行

        (a)Execute方法 源码

int c = ctl.get();//拿到当前线程的状态值(高3位)
if (workerCountOf(c) < corePoolSize) {//当线程总数量<核心线程池大小,就会直接处理任务
    if (addWorker(command, true))
        return;
    c = ctl.get();
}
if (isRunning(c) && workQueue.offer(command)) {
    int recheck = ctl.get();
    if (! isRunning(recheck) && remove(command))
        reject(command);
    else if (workerCountOf(recheck) == 0)
        addWorker(null, false);
}
else if (!addWorker(command, false))
 reject(command);

(4)线程池的关闭

pool.shutdown()或者pool.shutdownNow()之后执行
while(!isTerminated()){
}

版权声明:本文为liulong99原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接:https://www.cnblogs.com/liulong99/p/11885555.html