1.问题引出
我们知道一个线程创建的时候就会附带一个Runnable任务,如果该Runable任务执行完毕后,该线程如何从线程池的等待队列中获取一个任务呢?
上一篇博客讲到线程池中线程和该线程的第一个任务封装在一个Worker类中,这个Worker类本身实现了Runnable接口,源码定义:
private final class Worker extends AbstractQueuedSynchronizer implements Runnable {
Worker(Runnable firstTask) {
setState(-1); // inhibit interrupts until runWorker
this.firstTask = firstTask;
this.thread = getThreadFactory().newThread(this);
}
public void run() {
runWorker(this);
}
}
通过构造函数可以知道,创建Worker对象就会创建一个线程,但是线程传递的参数是this,即该Worker对象,会不会感到很奇怪?!为什么不直接把firstTask传递给新创建的线程呢?!这是一个很关键的点,如果如我们所愿,firstTask任务直接传递给新线程,那么当firstTask执行完之后,该线程如何获取队列中的任务呢?或许你有更好的方法,但这里采用下面这种思想:把去等待队列中获取任务的过程封装成一个Runnable任务(就是该Worker对象),新创建的线程启动后,就会执行该Runnable任务,该Runnable任务执行完firstTask任务后,就会不断的从等待队列中获取任务,直到等待队列为空,该线程才会销毁。
下面详细分析这个过程,主要体现在runWorker(Worker)和getTask()方法内。
2.runWorker(Worker)
Worker对象,即Runnable任务的run()方法执行runWorker(this)方法:
final void runWorker(Worker w) {
Thread wt = Thread.currentThread(); // 获取当前线程
Runnable task = w.firstTask