线程池源码阅读(一)
仅大致过了下,有问题的请指出,谢谢。
版本
1.8
类关系
1. Executors
提供创建ThreadPoolExecutor
类的快速方法。
建议:不要使用Executors
类创建ThreadPoolExecutor
newFixedThreadPool
newSingleThreadExecutor
newCachedThreadPool
newScheduledThreadPool
public static ExecutorService newFixedThreadPool(int nThreads) {
return new ThreadPoolExecutor(nThreads, nThreads,
0L, TimeUnit.MILLISECONDS,
new LinkedBlockingQueue<Runnable>());
}
public static ExecutorService newFixedThreadPool(int nThreads, ThreadFactory threadFactory) {
return new ThreadPoolExecutor(nThreads, nThreads,
0L, TimeUnit.MILLISECONDS,
new LinkedBlockingQueue<Runnable>(),
threadFactory);
}
public static ExecutorService newSingleThreadExecutor() {
return new FinalizableDelegatedExecutorService
(new ThreadPoolExecutor(1, 1,
0L, TimeUnit.MILLISECONDS,
new LinkedBlockingQueue<Runnable>()));
}
public static ExecutorService newSingleThreadExecutor(ThreadFactory threadFactory) {
return new FinalizableDelegatedExecutorService
(new ThreadPoolExecutor(1, 1,
0L, TimeUnit.MILLISECONDS,
new LinkedBlockingQueue<Runnable>(),
threadFactory));
}
public static ExecutorService newCachedThreadPool() {
return new ThreadPoolExecutor(0, Integer.MAX_VALUE,
60L, TimeUnit.SECONDS,
new SynchronousQueue<Runnable>());
}
public static ExecutorService newCachedThreadPool(ThreadFactory threadFactory) {
return new ThreadPoolExecutor(0, Integer.MAX_VALUE,
60L, TimeUnit.SECONDS,
new SynchronousQueue<Runnable>(),
threadFactory);
}
public static ScheduledExecutorService newScheduledThreadPool(int corePoolSize) {
return new ScheduledThreadPoolExecutor(corePoolSize);
}
原因一:线程数量无限制
newCachedThreadPool
和ScheduledThreadPoolExecutor
的构造器,最大线程数量为:Integer.MAX_VALUE
。若大量任务进来,开辟大量新线程,直至OOM(内存溢出)。
public ScheduledThreadPoolExecutor(int corePoolSize) {
super(corePoolSize, Integer.MAX_VALUE, 0, NANOSECONDS,
new DelayedWorkQueue());
}
原因二:任务队列无边界
newFixedThreadPool
和newSingleThreadExecutor
的构造器,使用的阻塞队列为LinkedBlockingQueue
,使用的其默认构造器,代码如下:队列容量为Integer.MAX_VALUE
。若大量任务进来,存到阻塞无边界队列,直至OOM(内存溢出)。
public LinkedBlockingQueue() {
this(Integer.MAX_VALUE);
}
2. ThreadFactory
static class DefaultThreadFactory implements ThreadFactory {
private static final AtomicInteger poolNumber = new AtomicInteger(1);
private final ThreadGroup group;
private final AtomicInteger threadNumber = new AtomicInteger(1);
private final String namePrefix;
DefaultThreadFactory() {
SecurityManager s = System.getSecurityManager();
group = (s != null) ? s.getThreadGroup() :
Thread.currentThread().getThreadGroup();
namePrefix = "pool-" +
poolNumber.getAndIncrement() +
"-thread-";
}
public Thread newThread(Runnable r) {
Thread t = new Thread(group, r,
namePrefix + threadNumber.getAndIncrement(),
0);
if (t.isDaemon())
t.setDaemon(false);
if (t.getPriority() != Thread.NORM_PRIORITY)
t.setPriority(Thread.NORM_PRIORITY);
return t;
}
}
3. ExecutorService
1)线程池组件
- 线程池管理器:创建、销毁线程池,添加任务
- 工作线程:循环执行任务
- 任务队列:没有线程用于执行任务时,暂时存放任务
- 任务接口:具体任务需实现的接口
2)线程池状态
如何存储线程池状态
private final AtomicInteger ctl
ctl是一个int,32位的原子int类对象,高3位存储线程池状态,低29位存储线程池线程数量。
线程池有哪些状态
状态 | 描述 |
---|---|
running | 接受新任务,处理队列任务 |
shutdown | 不接受新任务,处理队列任务 |
stop | 不接受新任务,不处理队列任务,中断正处理的任务 |
tidying | 所有任务终止,线程数为0,线程池转为tidying |
terminated | terminated() 方法已完成 |
线程池状态切换
running -> shutdown:调用shutdown()
或finalize()
。
(running, shutdown) -> stop:调用shutdownNow()
。
shutdown -> tidying:任务队列和线程池都为空。
stop -> tidying:池为空。
tidying -> terminated:terminated()
,一个hook(钩子)方法。
3)方法列表
// 切换池状态为:shutdown。处理正执行任务,不接受新任务
void shutdown();
// 试图中断正执行任务,不处理任务队列的任务,并不接受新任务
List<Runnable> shutdownNow();
// 非运行态,返回true
boolean isShutdown();
// 非运行态,且小于TERMINATED,返回true:SHUTDOWN、STOP、TIDYING
boolean isTerminated();
// 等待:若线程池状态为TERMINATED,返回true;若超时,返回false
boolean awaitTermination(long timeout, TimeUnit unit)
// 提交一个任务
. submit(..);
// 执行所有任务。具体实现见:AbstractExecutorService
<T> T invoke[Xxx](Collection<? extends Callable<T>> tasks);
<T> T invoke[Xxx](Collection<? extends Callable<T>> tasks, long timeout, TimeUnit unit);
4. ThreadPoolExecutor
1)属性
// 值为:1110 0000 .. 0000(32位)
private final AtomicInteger ctl = new AtomicInteger(ctlOf(RUNNING, 0));
private final ReentrantLock mainLock = new ReentrantLock();
private final Condition termination = mainLock.newCondition();
private final BlockingQueue<Runnable> workQueue;
private final HashSet<Worker> workers = new HashSet<Worker>();
private volatile ThreadFactory threadFactory;
private volatile RejectedExecutionHandler handler;
private static final RejectedExecutionHandler defaultHandler = new AbortPolicy();
private long completedTaskCount;
private volatile long keepAliveTime;
private volatile int corePoolSize;
private volatile int maximumPoolSize;
2)构造器
- 核心线程
- 最大线程
- 临时线程的存活时间
- 任务队列
- 线程工厂
- 拒绝策略
3)拒绝策略
顶层接口
public interface RejectedExecutionHandler {
void rejectedExecution(Runnable r, ThreadPoolExecutor executor);
}
实现:4
CallerRunsPolicy
public void rejectedExecution(Runnable r, ThreadPoolExecutor e) {
if (!e.isShutdown()) {
r.run();
}
}
AbortPolicy:默认
public void rejectedExecution(Runnable r, ThreadPoolExecutor e) {
throw new RejectedExecutionException("Task " + r.toString() +
" rejected from " +
e.toString());
}
DiscardPolicy
//不做处理,即丢弃
DiscardOldestPolicy
public void rejectedExecution(Runnable r, ThreadPoolExecutor e) {
if (!e.isShutdown()) {
e.getQueue().poll();
e.execute(r);
}
}
4)提交任务策略
1. 线程池运行线程数running < 核心线程数core
开启新线程
2. running >= core
提交任务到阻塞队列
队列未满,提交成功;
队列已满
running < max
3. running >= core && 队列已满
running < max,创建新线程
running = max,执行拒绝策略
public Future<?> submit(Runnable task) {
if (task == null) throw new NullPointerException();
RunnableFuture<Void> ftask = newTaskFor(task, null);
execute(ftask);
return ftask;
}
public void execute(Runnable command) {
if (command == null)
throw new NullPointerException();
int c = ctl.get();
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);
}
private boolean addWorker(Runnable firstTask, boolean core) {
retry:
for (;;) {
int c = ctl.get();
int rs = runStateOf(c);
// Check if queue empty only if necessary.
if (rs >= SHUTDOWN &&
! (rs == SHUTDOWN &&
firstTask == null &&
! workQueue.isEmpty()))
return false;
for (;;) {
int wc = workerCountOf(c);
if (wc >= CAPACITY ||
wc >= (core ? corePoolSize : maximumPoolSize))
return false;
if (compareAndIncrementWorkerCount(c))
break retry;
c = ctl.get(); // Re-read ctl
if (runStateOf(c) != rs)
continue retry;
// else CAS failed due to workerCount change; retry inner loop
}
}
boolean workerStarted = false;
boolean workerAdded = false;
Worker w = null;
try {
w = new Worker(firstTask);
final Thread t = w.thread;
if (t != null) {
final ReentrantLock mainLock = this.mainLock;
mainLock.lock();
try {
// Recheck while holding lock.
// Back out on ThreadFactory failure or if
// shut down before lock acquired.
int rs = runStateOf(ctl.get());
if (rs < SHUTDOWN ||
(rs == SHUTDOWN && firstTask == null)) {
if (t.isAlive()) // precheck that t is startable
throw new IllegalThreadStateException();
workers.add(w);
int s = workers.size();
if (s > largestPoolSize)
largestPoolSize = s;
workerAdded = true;
}
} finally {
mainLock.unlock();
}
if (workerAdded) {
t.start();
workerStarted = true;
}
}
} finally {
if (! workerStarted)
addWorkerFailed(w);
}
return workerStarted;
}
参考
https://juejin.im/entry/59b232ee6fb9a0248d25139a#threadpoolexecutor``
https://juejin.im/post/5b3cf259e51d45194e0b7204#heading-28
https://blog.csdn.net/u012240455/article/details/81844007
来源:CSDN
作者:清澈。初见
链接:https://blog.csdn.net/qq_31854267/article/details/104009118