目錄
3、completeNull / completeValue / completeThrowable / completeRelay
4、thenApply / thenAccept / thenRun
5、UniApply / UniAccept / UniRun
7、get / join / getNow / cancel
上一篇《Java8 CompletableFuture 用法全解》探討了CompletableFuture的用法,本篇博客就詳細探討該類的實現細節。
1、定義
CompletableFuture的類繼承關係如下:
CompletionStage是Java8引入的支持異步回調和多個任務組合處理的Future接口的增強版,上篇博客中介紹的thenApply,thenApply等方法都是該接口定義的,CompletableFuture是該接口的唯一實現類。該類包含的屬性如下:
//任務的執行結果或者異常信息
volatile Object result; // Either the result or boxed AltResult
volatile Completion stack; // Top of Treiber stack of dependent actions
static final AltResult NIL = new AltResult(null);
//是否使用common線程池,如果是多核處理器則是true
private static final boolean useCommonPool =
(ForkJoinPool.getCommonPoolParallelism() > 1);
//默認的Executor實現
private static final Executor asyncPool = useCommonPool ?
ForkJoinPool.commonPool() : new ThreadPerTaskExecutor();
//tryFire的三種模式,
//SYNC表示同步調用
static final int SYNC = 0;
//ASYNC表示異步調用
static final int ASYNC = 1;
//NESTED表示內部調用
static final int NESTED = -1;
其中Completion是一個繼承自ForkJoinTask的抽象內部類,其定義如下:
通過next屬性多個Completion便構成了鏈表關係。Completion有多個子類,這些子類就是CompletionStage接口實現的核心,如下圖:
後面會相信介紹相關子類的實現。AltResult和ThreadPerTaskExecutor都是內部類,其定義如下:
除上述屬性外,還有多個表示字段偏移量的屬性,通過static代碼塊初始化,如下:
該類對外的構造方法只有默認的無參構造方法,不設置任何屬性,如下:
2、supplyAsync / runAsync
這兩個方法都是用來創建異步任務並提交到線程池中,可通過返回的CompletableFuture實例獲取任務執行的狀態和結果,區別在於supplyAsync有返回值而runAsync無返回值。
public static <U> CompletableFuture<U> supplyAsync(Supplier<U> supplier) {
return asyncSupplyStage(asyncPool, supplier);
}
public static <U> CompletableFuture<U> supplyAsync(Supplier<U> supplier,
Executor executor) {
return asyncSupplyStage(screenExecutor(executor), supplier);
}
public static CompletableFuture<Void> runAsync(Runnable runnable) {
return asyncRunStage(asyncPool, runnable);
}
public static CompletableFuture<Void> runAsync(Runnable runnable,
Executor executor) {
return asyncRunStage(screenExecutor(executor), runnable);
}
static <U> CompletableFuture<U> asyncSupplyStage(Executor e,
Supplier<U> f) {
if (f == null) throw new NullPointerException();
CompletableFuture<U> d = new CompletableFuture<U>();
//提交異步任務,會調用AsyncSupply的run方法
e.execute(new AsyncSupply<U>(d, f));
//可以根據實例d獲取f的執行狀態和結果
return d;
}
static Executor screenExecutor(Executor e) {
if (!useCommonPool && e == ForkJoinPool.commonPool())
return asyncPool; //如果useCommonPool爲false,則不能使用common線程池
if (e == null) throw new NullPointerException();
return e;
}
static CompletableFuture<Void> asyncRunStage(Executor e, Runnable f) {
if (f == null) throw new NullPointerException();
CompletableFuture<Void> d = new CompletableFuture<Void>();
//提交異步任務
e.execute(new AsyncRun(d, f));
return d;
}
其中AsyncSupply和AsyncRun都是兩個繼承自ForkJoinTask的內部類,其實現如下:
static final class AsyncSupply<T> extends ForkJoinTask<Void>
implements Runnable, AsynchronousCompletionTask {
CompletableFuture<T> dep; Supplier<T> fn;
//注意dep會被返回,用於獲取fn的執行狀態和執行結果,而不是AsyncSupply本身
AsyncSupply(CompletableFuture<T> dep, Supplier<T> fn) {
this.dep = dep; this.fn = fn;
}
public final Void getRawResult() { return null; }
public final void setRawResult(Void v) {}
public final boolean exec() { run(); return true; }
public void run() {
CompletableFuture<T> d; Supplier<T> f;
if ((d = dep) != null && (f = fn) != null) {
dep = null; fn = null;
if (d.result == null) { //還未執行
try {
//執行f.get就是執行異步任務,並通過completeValue保存結果
d.completeValue(f.get());
} catch (Throwable ex) {
//執行異常,保存異常信息
d.completeThrowable(ex);
}
}
//做事後處理
d.postComplete();
}
}
}
static final class AsyncRun extends ForkJoinTask<Void>
implements Runnable, AsynchronousCompletionTask {
CompletableFuture<Void> dep; Runnable fn;
//同上dep會被返回
AsyncRun(CompletableFuture<Void> dep, Runnable fn) {
this.dep = dep; this.fn = fn;
}
public final Void getRawResult() { return null; }
public final void setRawResult(Void v) {}
public final boolean exec() { run(); return true; }
public void run() {
CompletableFuture<Void> d; Runnable f;
if ((d = dep) != null && (f = fn) != null) {
dep = null; fn = null;
if (d.result == null) {
try {
f.run();
//執行完成,設置返回值爲null
d.completeNull();
} catch (Throwable ex) {
//執行異常,保存異常信息
d.completeThrowable(ex);
}
}
//做事後處理
d.postComplete();
}
}
}
3、completeNull / completeValue / completeThrowable / completeRelay
這幾個方法都是CAS修改result屬性,保存任務執行的結果或者執行異常時拋出的異常信息。
final boolean completeNull() {
//cas修改result屬性
return UNSAFE.compareAndSwapObject(this, RESULT, null,
NIL);
}
final boolean completeValue(T t) {
return UNSAFE.compareAndSwapObject(this, RESULT, null,
(t == null) ? NIL : t);
}
final boolean completeThrowable(Throwable x) {
return UNSAFE.compareAndSwapObject(this, RESULT, null,
encodeThrowable(x));
}
final boolean completeThrowable(Throwable x, Object r) {
return UNSAFE.compareAndSwapObject(this, RESULT, null,
encodeThrowable(x, r));
}
final boolean completeRelay(Object r) {
return UNSAFE.compareAndSwapObject(this, RESULT, null,
encodeRelay(r));
}
//將x用CompletionException包裝一層
static AltResult encodeThrowable(Throwable x) {
return new AltResult((x instanceof CompletionException) ? x :
new CompletionException(x));
}
//使用CompletionException 或者 AltResult包裝一層
static Object encodeThrowable(Throwable x, Object r) {
if (!(x instanceof CompletionException))
x = new CompletionException(x);
else if (r instanceof AltResult && x == ((AltResult)r).ex)
return r;
return new AltResult(x);
}
static Object encodeRelay(Object r) {
Throwable x;
return (((r instanceof AltResult) &&
(x = ((AltResult)r).ex) != null &&
!(x instanceof CompletionException)) ?
new AltResult(new CompletionException(x)) : r);
}
4、thenApply / thenAccept / thenRun
thenApply的三個方法其實現都是uniApplyStage,如下:
public <U> CompletableFuture<U> thenApply(
Function<? super T,? extends U> fn) {
return uniApplyStage(null, fn);
}
public <U> CompletableFuture<U> thenApplyAsync(
Function<? super T,? extends U> fn) {
//不指定executor,默認使用asyncPool
return uniApplyStage(asyncPool, fn);
}
public <U> CompletableFuture<U> thenApplyAsync(
Function<? super T,? extends U> fn, Executor executor) {
//使用指定的Executor實現
return uniApplyStage(screenExecutor(executor), fn);
}
thenAccept的實現是uniAcceptStage,thenRun的實現都是uniRunStage,都同thenApply,不意義列舉了,重點關注這三個私有方法的實現,如下:
//實現thenApply方法
private <V> CompletableFuture<V> uniApplyStage(
Executor e, Function<? super T,? extends V> f) {
if (f == null) throw new NullPointerException();
CompletableFuture<V> d = new CompletableFuture<V>();
//e爲null,則通過uniApply嘗試執行任務,返回false表示當前任務不可執行,返回true表示已執行
if (e != null || !d.uniApply(this, f, null)) {
//e不爲null 或者e爲null,後面的uniApply方法返回false
UniApply<T,V> c = new UniApply<T,V>(e, d, this, f);
//將c加入到stack鏈表中
push(c);
//嘗試同步執行任務
c.tryFire(SYNC);
}
return d;
}
final <S> boolean uniApply(CompletableFuture<S> a,
Function<? super S,? extends T> f,
UniApply<S,T> c) {
Object r; Throwable x;
//a.result爲null說明a未執行完成
if (a == null || (r = a.result) == null || f == null)
return false; //三個條件任意一個成立,則返回false
//三個都不爲null,a已執行完成
tryComplete:
if (result == null) { //當前result屬性爲null
if (r instanceof AltResult) {
if ((x = ((AltResult)r).ex) != null) {
//a是異常終止的,將當前任務標記爲異常終止
completeThrowable(x, r);
break tryComplete; //終止處理
}
//a是正常結束
r = null;
}
try {
//claim返回false,表示異步執行,返回true表示由當前線程執行任務
if (c != null && !c.claim())
return false;
//c爲null 或者 c.claim爲true
//將上一個任務a的執行結果作爲參數傳遞給f
@SuppressWarnings("unchecked") S s = (S) r;
//執行f並保存執行結果
completeValue(f.apply(s));
} catch (Throwable ex) {
//執行異常,保存異常信息
completeThrowable(ex);
}
} //最外層的if
return true;
}
//實現thenAccept方法,整體邏輯同uniApplyStage
private CompletableFuture<Void> uniAcceptStage(Executor e,
Consumer<? super T> f) {
if (f == null) throw new NullPointerException();
CompletableFuture<Void> d = new CompletableFuture<Void>();
if (e != null || !d.uniAccept(this, f, null)) {
UniAccept<T> c = new UniAccept<T>(e, d, this, f);
push(c);
c.tryFire(SYNC);
}
return d;
}
final <S> boolean uniAccept(CompletableFuture<S> a,
Consumer<? super S> f, UniAccept<S> c) {
Object r; Throwable x;
if (a == null || (r = a.result) == null || f == null)
return false;
tryComplete: if (result == null) {
if (r instanceof AltResult) {
if ((x = ((AltResult)r).ex) != null) {
completeThrowable(x, r);
break tryComplete;
}
r = null;
}
try {
if (c != null && !c.claim())
return false;
@SuppressWarnings("unchecked") S s = (S) r;
//執行f,因爲accept方法無返回值,此時設置返回值爲特定表示NULL的值
f.accept(s);
completeNull();
} catch (Throwable ex) {
completeThrowable(ex);
}
}
return true;
}
//實現thenRun方法,整體邏輯同uniApplyStage
private CompletableFuture<Void> uniRunStage(Executor e, Runnable f) {
if (f == null) throw new NullPointerException();
CompletableFuture<Void> d = new CompletableFuture<Void>();
if (e != null || !d.uniRun(this, f, null)) {
UniRun<T> c = new UniRun<T>(e, d, this, f);
push(c);
c.tryFire(SYNC);
}
return d;
}
final boolean uniRun(CompletableFuture<?> a, Runnable f, UniRun<?> c) {
Object r; Throwable x;
if (a == null || (r = a.result) == null || f == null)
return false;
if (result == null) {
if (r instanceof AltResult && (x = ((AltResult)r).ex) != null)
completeThrowable(x, r); //a執行異常,將當前任務標記爲異常結束
else
try {
if (c != null && !c.claim())
return false;
//因爲f沒有參數,所以不需要關注a的執行結果
//執行f,因爲accept方法無返回值,此時設置返回值爲特定表示NULL的值
f.run();
completeNull();
} catch (Throwable ex) {
completeThrowable(ex);
}
}
return true;
}
final void push(UniCompletion<?,?> c) {
if (c != null) {
//result等於null,說明任務未完成
//不斷while循環,直到將c插入到stack鏈表中
while (result == null && !tryPushStack(c))
lazySetNext(c, null); //如果tryPushStack返回false,將c的next屬性置爲null
}
}
5、UniApply / UniAccept / UniRun
這三個都是繼承自UniCompletion,其實現如下:
abstract static class UniCompletion<T,V> extends Completion {
//執行任務的線程池實現
Executor executor; // executor to use (null if none)
//當前任務
CompletableFuture<V> dep; // the dependent to complete
//上一個任務
CompletableFuture<T> src; // source for action
UniCompletion(Executor executor, CompletableFuture<V> dep,
CompletableFuture<T> src) {
this.executor = executor; this.dep = dep; this.src = src;
}
//如果executor不爲空,則通過線程池異步執行此任務,返回false,否則返回true,由
//調用此方法的線程負責執行當前任務
final boolean claim() {
Executor e = executor;
if (compareAndSetForkJoinTaskTag((short)0, (short)1)) {
//cas修改tag,表明是當前線程佔有了該任務,避免被重複執行
if (e == null)
return true;
//e不爲null,通過e執行當前任務,執行tryFire(ASYNC)
executor = null; // disable
e.execute(this);
}
return false;
}
final boolean isLive() { return dep != null; }
}
static final class UniApply<T,V> extends UniCompletion<T,V> {
Function<? super T,? extends V> fn;
UniApply(Executor executor, CompletableFuture<V> dep,
CompletableFuture<T> src,
Function<? super T,? extends V> fn) {
super(executor, dep, src); this.fn = fn;
}
final CompletableFuture<V> tryFire(int mode) {
CompletableFuture<V> d; CompletableFuture<T> a;
if ((d = dep) == null ||
//dep不爲null,說明當前任務未執行,則調用uniApply嘗試執行任務
//如果mode不是NESTED,則第三個參數爲null,否則爲this,如果不是null,則需要調用claim方法判斷是否由當前線程執行
//uniApply返回false表示當前線程不能執行該任務
!d.uniApply(a = src, fn, mode > 0 ? null : this))
return null;
//執行完成,將各屬性置爲null
dep = null; src = null; fn = null;
//執行事後處理
return d.postFire(a, mode);
}
}
static final class UniAccept<T> extends UniCompletion<T,Void> {
Consumer<? super T> fn;
UniAccept(Executor executor, CompletableFuture<Void> dep,
CompletableFuture<T> src, Consumer<? super T> fn) {
super(executor, dep, src); this.fn = fn;
}
//邏輯同UniApply
final CompletableFuture<Void> tryFire(int mode) {
CompletableFuture<Void> d; CompletableFuture<T> a;
if ((d = dep) == null ||
!d.uniAccept(a = src, fn, mode > 0 ? null : this))
return null;
dep = null; src = null; fn = null;
return d.postFire(a, mode);
}
}
static final class UniRun<T> extends UniCompletion<T,Void> {
Runnable fn;
UniRun(Executor executor, CompletableFuture<Void> dep,
CompletableFuture<T> src, Runnable fn) {
super(executor, dep, src); this.fn = fn;
}
//邏輯同UniApply
final CompletableFuture<Void> tryFire(int mode) {
CompletableFuture<Void> d; CompletableFuture<T> a;
if ((d = dep) == null ||
!d.uniRun(a = src, fn, mode > 0 ? null : this))
return null;
dep = null; src = null; fn = null;
return d.postFire(a, mode);
}
}
//ForkJoinTask的方法
public final boolean compareAndSetForkJoinTaskTag(short e, short tag) {
for (int s;;) {
if ((short)(s = status) != e) //如果當前status的低16位不是e則返回
return false;
//SMASK獲取status的低16位
if (U.compareAndSwapInt(this, STATUS, s,
(s & ~SMASK) | (tag & SMASK)))
//cas修改status,加上tag
return true;
}
}
6、postComplete / postFire
postComplete是在某個異步任務執行完成後觸發回調方法的,postFire是在回調方法執行完成後觸發下一個回調方法的,這兩方法的調用鏈如下:
final void postComplete() {
/*
* On each step, variable f holds current dependents to pop
* and run. It is extended along only one path at a time,
* pushing others to avoid unbounded recursion.
*/
CompletableFuture<?> f = this; Completion h;
while ((h = f.stack) != null || //此時f不一定是this
//如果f.stack爲null,重置f等於this
(f != this && (h = (f = this).stack) != null)) {
//stack屬性不爲空
CompletableFuture<?> d; Completion t;
//cas修改stack屬性,由h改成其next屬性
if (f.casStack(h, t = h.next)) {
if (t != null) {
//可能還有下一個next,Uni類操作next屬性都爲null,因爲每次操作都返回一個新的CompletableFuture實例
if (f != this) {
//將h加入到當前CompletableFuture的stack鏈表
pushStack(h);
//重新開始下一次while循環
continue;
}
//next置爲null,從鏈表中移除
h.next = null; // detach
}
//t爲null 或者t不爲null,f爲this時,觸發h節點的執行
//如果Executor不爲空,則此時會觸發該任務的異步執行,返回null,如果爲空,則觸發同步執行
//tryFire返回null時,f等於this,即重試,不爲null時,f等於d,即處理下一個節點
f = (d = h.tryFire(NESTED)) == null ? this : d;
}
}
}
final CompletableFuture<T> postFire(CompletableFuture<?> a,
CompletableFuture<?> b, int mode) {
if (b != null && b.stack != null) { // clean second source
//如果是NESTED調用或者a未執行
if (mode < 0 || b.result == null)
b.cleanStack();
else
b.postComplete();
}
return postFire(a, mode);
}
final CompletableFuture<T> postFire(CompletableFuture<?> a, int mode) {
//stack不爲null,說明還有下一個待執行的任務
if (a != null && a.stack != null) {
//如果是NESTED調用或者a未執行
if (mode < 0 || a.result == null)
a.cleanStack(); //將已執行的任務從stack鏈表中移除
else
a.postComplete();
}
if (result != null && stack != null) {
//當前CompletableFuture已執行
if (mode < 0)
return this; //如果是NESTED調用
else
postComplete(); //如果是SYNC 或者 ASYNC調用
}
return null;
}
final boolean casStack(Completion cmp, Completion val) {
return UNSAFE.compareAndSwapObject(this, STACK, cmp, val);
}
final void pushStack(Completion c) {
//不斷重試直到插入到stack鏈表
do {} while (!tryPushStack(c));
}
final boolean tryPushStack(Completion c) {
Completion h = stack;
//cas修改next屬性
lazySetNext(c, h);
//修改stack屬性,有h改成c,即將c插入到h的前面
return UNSAFE.compareAndSwapObject(this, STACK, h, c);
}
static void lazySetNext(Completion c, Completion next) {
UNSAFE.putOrderedObject(c, NEXT, next);
}
//清楚stack鏈表中非live 即任務已經執行的節點
final void cleanStack() {
//p表示上一個live的節點,會把stack鏈表中所有元素都遍歷一遍
for (Completion p = null, q = stack; q != null;) {
Completion s = q.next;
if (q.isLive()) {
p = q;
q = s; //即遍歷下一個節點
}
//q.isLive爲false
else if (p == null) {
//修改stack,將q從stack鏈表移除
casStack(q, s);
//重新讀取stack屬性
q = stack;
}
else {
//p不爲null
p.next = s;
if (p.isLive())
q = s;
else {
p = null; //p原來是live的,現在不是live,說明遍歷期間可能多個任務執行完了,則從頭開始遍歷
q = stack;
}
}
}
}
7、get / join / getNow / cancel
get方法和join方法都是阻塞當前線程等待任務完成並返回任務執行的結果,兩者的區別在於拋出的異常類型稍有不同,join方法在線程被中斷的情形下不會拋出異常,而get方法會拋出異常。get方法還可以指定等待的超時時間,getNow方法是立即獲取執行結果,如果爲null,則返回指定的默認值。cancel方法用於取消某個任務,如果任務未執行完成,result爲null則設置特定的異常對象表示該任務已取消。
public T get() throws InterruptedException, ExecutionException {
Object r;
//如果result爲null,則調用waitingGet等待結果,否則調用reportGet
return reportGet((r = result) == null ? waitingGet(true) : r);
}
public T get(long timeout, TimeUnit unit)
throws InterruptedException, ExecutionException, TimeoutException {
Object r;
//轉換單位
long nanos = unit.toNanos(timeout);
return reportGet((r = result) == null ? timedGet(nanos) : r);
}
public T getNow(T valueIfAbsent) {
Object r;
//如果result爲null,則返回指定的默認值 valueIfAbsent,否則reportJoin
return ((r = result) == null) ? valueIfAbsent : reportJoin(r);
}
public T join() {
Object r;
//同get,主要拋出的異常類型不同,注意waitingGet傳遞false,不響應線程中斷
return reportJoin((r = result) == null ? waitingGet(false) : r);
}
//取消任務,返回true表示任務已取消,返回false表示任務已執行完成
public boolean cancel(boolean mayInterruptIfRunning) {
//如果result爲null,則設置一個AltResult,表示任務已取消
boolean cancelled = (result == null) &&
internalComplete(new AltResult(new CancellationException()));
//執行事後處理
postComplete();
return cancelled || isCancelled();
}
final boolean internalComplete(Object r) { // CAS from null to r
return UNSAFE.compareAndSwapObject(this, RESULT, null, r);
}
//判斷任務是否已取消
public boolean isCancelled() {
Object r;
return ((r = result) instanceof AltResult) &&
(((AltResult)r).ex instanceof CancellationException);
}
private static <T> T reportGet(Object r)
throws InterruptedException, ExecutionException {
if (r == null) //被中斷了,返回null,拋出異常
throw new InterruptedException();
if (r instanceof AltResult) {
Throwable x, cause;
if ((x = ((AltResult)r).ex) == null) //就是NIL
return null;
if (x instanceof CancellationException) //被取消
throw (CancellationException)x;
if ((x instanceof CompletionException) && //執行異常
(cause = x.getCause()) != null)
x = cause;
throw new ExecutionException(x);
}
@SuppressWarnings("unchecked") T t = (T) r;
return t;
}
private static <T> T reportJoin(Object r) {
if (r instanceof AltResult) {
Throwable x;
if ((x = ((AltResult)r).ex) == null)
return null;
if (x instanceof CancellationException)
throw (CancellationException)x;
if (x instanceof CompletionException)
throw (CompletionException)x;
throw new CompletionException(x);
}
@SuppressWarnings("unchecked") T t = (T) r;
return t;
}
private Object waitingGet(boolean interruptible) {
Signaller q = null;
boolean queued = false;
int spins = -1;
Object r;
while ((r = result) == null) {
if (spins < 0)
//如果是多核,則自旋64次
spins = (Runtime.getRuntime().availableProcessors() > 1) ?
1 << 8 : 0; // Use brief spin-wait on multiprocessors
else if (spins > 0) {
if (ThreadLocalRandom.nextSecondarySeed() >= 0)
--spins; //自旋等待
}
else if (q == null) //初始化q
q = new Signaller(interruptible, 0L, 0L);
else if (!queued) //將q加入到stack鏈表中
queued = tryPushStack(q);
else if (interruptible && q.interruptControl < 0) {
//如果響應中斷,且當前線程被中斷了
q.thread = null;
cleanStack(); //將q從stack鏈表中移除
return null;
}
else if (q.thread != null && result == null) {
try {
//阻塞當前線程
ForkJoinPool.managedBlock(q);
} catch (InterruptedException ie) {
//被中斷
q.interruptControl = -1;
}
}
}
//r不爲null
if (q != null) {
q.thread = null;
if (q.interruptControl < 0) {
if (interruptible) //如果響應中斷,將r置爲null
r = null; // report interruption
else
//不響應中斷,將當前線程標記爲中斷
Thread.currentThread().interrupt();
}
}
//執行事後處理
postComplete();
//返回結果
return r;
}
//跟waitingGet類似,區別在於必須響應中斷,有等待時間限制,如果超時則拋出異常TimeoutException
private Object timedGet(long nanos) throws TimeoutException {
if (Thread.interrupted()) //線程已中斷
return null;
if (nanos <= 0L) //不需要等待
throw new TimeoutException();
long d = System.nanoTime() + nanos;
Signaller q = new Signaller(true, nanos, d == 0L ? 1L : d); // avoid 0
boolean queued = false;
Object r;
while ((r = result) == null) {
if (!queued) //加入到stack隊列中
queued = tryPushStack(q);
else if (q.interruptControl < 0 || q.nanos <= 0L) {
//被中斷或者等待超時
q.thread = null;
cleanStack(); //將q從Stack隊列中移除
if (q.interruptControl < 0) //被中斷 返回null
return null;
throw new TimeoutException(); //等待超時,拋出異常
}
else if (q.thread != null && result == null) {
try {
//阻塞當前線程
ForkJoinPool.managedBlock(q);
} catch (InterruptedException ie) {
q.interruptControl = -1; //被中斷了
}
}
}
//result不爲null
if (q.interruptControl < 0)
r = null;
q.thread = null;
postComplete();
return r;
}
8、Signaller
Signaller表示一個等待的線程關聯的節點,由get /join方法使用,其調用鏈如下:
其實現如下:
@SuppressWarnings("serial")
static final class Signaller extends Completion
implements ForkJoinPool.ManagedBlocker {
long nanos; // wait time if timed
final long deadline; // non-zero if timed
volatile int interruptControl; // > 0: interruptible, < 0: interrupted
volatile Thread thread;
//interruptible表示是否響應中斷
//nanos表示等待的時間,deadline表示等待的終止時間
Signaller(boolean interruptible, long nanos, long deadline) {
this.thread = Thread.currentThread();
this.interruptControl = interruptible ? 1 : 0;
this.nanos = nanos;
this.deadline = deadline;
}
//當任務執行完成後會調用此方法喚醒等待的線程
final CompletableFuture<?> tryFire(int ignore) {
Thread w; // no need to atomically claim
if ((w = thread) != null) {
thread = null;
//喚醒等待的線程
LockSupport.unpark(w);
}
return null;
}
//返回true表示可以終止阻塞了,返回false表示需要繼續阻塞
public boolean isReleasable() {
if (thread == null) //已經執行tryFire了
return true;
if (Thread.interrupted()) { //線程被中斷
int i = interruptControl;
interruptControl = -1;
if (i > 0) //需要響應中斷,返回true,終止阻塞
return true;
}
if (deadline != 0L &&
(nanos <= 0L || (nanos = deadline - System.nanoTime()) <= 0L)) {
thread = null; //等待超時
return true;
}
return false;
}
//將線程阻塞
public boolean block() {
if (isReleasable())
return true;
else if (deadline == 0L)
LockSupport.park(this);
else if (nanos > 0L)
LockSupport.parkNanos(this, nanos);
return isReleasable();
}
//如果執行了tryFire,則thread爲null,isLive返回false
final boolean isLive() { return thread != null; }
}