2)構(gòu)造方法
public FutureTask(Callable<V> callable) {if (callable == null)throw new NullPointerException();this.callable = callable;this.state = NEW;// ensure visibility of callable}public FutureTask(Runnable runnable, V result) {//封裝成callable,但返回值為傳入的值this.callable = Executors.callable(runnable, result);this.state = NEW;}3)核心方法
1.run()方法
public void run() {if (state != NEW || !UNSAFE.compareAndSwapObject(this, runnerOffset, null, Thread.currentThread()))return;// 只有當(dāng)任務(wù)狀態(tài)為new并且runner舊值為null才會(huì)執(zhí)行到這里try {Callable<V> c = callable;if (c != null && state == NEW) {V result;boolean ran;try {// 調(diào)用callable.run()并返回結(jié)果result = c.call();ran = true;} catch (Throwable ex) {result = null;ran = false;setException(ex);}if (ran)// 內(nèi)部設(shè)置outcome為callable執(zhí)行的結(jié)果,并且更新任務(wù)的狀態(tài)為NORMAL(任務(wù)正常執(zhí)行)并且喚醒阻塞的線程set(result);}} finally {runner = null;int s = state;if (s >= INTERRUPTING)// 如果當(dāng)前任務(wù)處于中斷中,則執(zhí)行這個(gè)方法線程會(huì)不斷讓出cpu直到任務(wù)處于已中斷狀態(tài)handlePossibleCancellationInterrupt(s);}}2.set(V v)方法
protected void set(V v) {if (UNSAFE.compareAndSwapInt(this, stateOffset, NEW, COMPLETING)) {// 設(shè)置outcome(結(jié)果)為callable.run()返回的結(jié)果outcome = v;//修改狀態(tài)UNSAFE.putOrderedInt(this, stateOffset, NORMAL); // final state// 喚醒調(diào)用get()的所有等待的線程并清空棧finishCompletion();}}protected void setException(Throwable t) {if (UNSAFE.compareAndSwapInt(this, stateOffset, NEW, COMPLETING)) {// 設(shè)置outcome(結(jié)果)為callable.run()拋出的異常outcome = t;UNSAFE.putOrderedInt(this, stateOffset, EXCEPTIONAL); // final statefinishCompletion();}}3.get()方法
【Future詳解】public V get() throws InterruptedException, ExecutionException {int s = state;// 條件成立會(huì)調(diào)用awaitDone方法自旋等待直到任務(wù)完成if (s <= COMPLETING) s = awaitDone(false, 0L);return report(s);}public V get(long timeout, TimeUnit unit) throws InterruptedException, ExecutionException, TimeoutException {if (unit == null)throw new NullPointerException();int s = state;if (s <= COMPLETING && (s = awaitDone(true, unit.toNanos(timeout))) <= COMPLETING)throw new TimeoutException();return report(s);}//這個(gè)方法是真正用來獲取任務(wù)的返回結(jié)果的,這個(gè)方法在get()方法里面會(huì)被調(diào)用,如果該方法被調(diào)用,說明任務(wù)已經(jīng)執(zhí)行完了 。private V report(int s) throws ExecutionException {Object x = outcome;if (s == NORMAL)return (V)x;if (s >= CANCELLED)throw new CancellationException();throw new ExecutionException((Throwable)x);}4.awaitDone(boolean timed, long nanos)方法
// 這個(gè)方法的作用是等待任務(wù)被完成(正常完成或出現(xiàn)異常完成都算完成),被中斷,或是被超時(shí)private int awaitDone(boolean timed, long nanos)throws InterruptedException {final long deadline = timed ? System.nanoTime() + nanos : 0L;WaitNode q = null;boolean queued = false;for (;;) {// 如果當(dāng)前線程出現(xiàn)中斷異常,則將該線程代表的WaitNode結(jié)點(diǎn)移出棧并拋出中斷異常if (Thread.interrupted()) {removeWaiter(q);throw new InterruptedException();}int s = state;// 如果當(dāng)前任務(wù)狀態(tài)大于COMPLETING,說明當(dāng)前任務(wù)已經(jīng)有結(jié)果了(任務(wù)完成、中斷、取消),直接返回任務(wù)狀態(tài)if (s > COMPLETING) {if (q != null)q.thread = null;return s;}// 當(dāng)前任務(wù)處于臨界狀態(tài),即將完成,則當(dāng)前線程釋放cpuelse if (s == COMPLETING) // cannot time out yetThread.yield();// 第一次自旋,如果當(dāng)前WitNode為null,new一個(gè)WaitNode結(jié)點(diǎn)else if (q == null)q = new WaitNode();// 第二次自旋,如果當(dāng)前WaitNode節(jié)點(diǎn)沒有入隊(duì),則嘗試入隊(duì)else if (!queued)queued = UNSAFE.compareAndSwapObject(this, waitersOffset,q.next = waiters, q);// 第三次自旋,到這里表示是否定義了超時(shí)時(shí)間else if (timed) {nanos = deadline - System.nanoTime();if (nanos <= 0L) {removeWaiter(q);return state;}// 未超出時(shí)間,掛起當(dāng)前線程一定時(shí)間LockSupport.parkNanos(this, nanos);}else// 掛起當(dāng)前線程,該線程會(huì)休眠(什么時(shí)候該線程會(huì)繼續(xù)執(zhí)行呢?除非有其他線程調(diào)用unpark()或者中斷該線程)LockSupport.park(this);}}
經(jīng)驗(yàn)總結(jié)擴(kuò)展閱讀
- Go的網(wǎng)絡(luò)編程詳解
- gorm中的關(guān)聯(lián)操作詳解
- Go中的閉包、遞歸
- liunx之expect操作詳解
- 條件期望:Conditional Expectation 舉例詳解之入門之入門之草履蟲都說聽懂了
- 深入理解AQS--jdk層面管程實(shí)現(xiàn)【管程詳解的補(bǔ)充】
- 從緩存入門到并發(fā)編程三要素詳解 Java中 volatile 、final 等關(guān)鍵字解析案例
- 補(bǔ)充部分---ScheduledThreadPoolExecutor類分析 線程池底層原理詳解與源碼分析
- Redis高并發(fā)分布式鎖詳解
- 5種分布式ID生成方案 分布式ID詳解
