溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務(wù)條款》

Java FutureTask類的用法

發(fā)布時間:2020-07-30 14:52:56 來源:億速云 閱讀:164 作者:小豬 欄目:編程語言

這篇文章主要講解了Java FutureTask類的用法,內(nèi)容清晰明了,對此有興趣的小伙伴可以學(xué)習(xí)一下,相信大家閱讀完之后會有幫助。

FutureTask一個可取消的異步計算,F(xiàn)utureTask 實現(xiàn)了Future的基本方法,提空 start cancel 操作,可以查詢計算是否已經(jīng)完成,并且可以獲取計算的結(jié)果。結(jié)果只可以在計算完成之后獲取,get方法會阻塞當(dāng)計算沒有完成的時候,一旦計算已經(jīng)完成,那么計算就不能再次啟動或是取消。

一個FutureTask 可以用來包裝一個 Callable 或是一個runnable對象。因為FurtureTask實現(xiàn)了Runnable方法,所以一個 FutureTask可以提交(submit)給一個Excutor執(zhí)行(excution).

FutureTask是java 5引入的一個類,從名字可以看出來FutureTask既是一個Future,又是一個Task。

我們看下FutureTask的定義:

public class FutureTask<V> implements RunnableFuture<V> {
  ...
}
public interface RunnableFuture<V> extends Runnable, Future<V> {
  /**
   * Sets this Future to the result of its computation
   * unless it has been cancelled.
   */
  void run();
}

FutureTask實現(xiàn)了RunnableFuture接口,RunnableFuture接口是Runnable和Future的綜合體。

作為一個Future,F(xiàn)utureTask可以執(zhí)行異步計算,可以查看異步程序是否執(zhí)行完畢,并且可以開始和取消程序,并取得程序最終的執(zhí)行結(jié)果。

除此之外,F(xiàn)utureTask還提供了一個runAndReset()的方法, 該方法可以運行task并且重置Future的狀態(tài)。

Callable和Runnable的轉(zhuǎn)換
我們知道Callable是有返回值的,而Runnable是沒有返回值的。
Executors提供了很多有用的方法,將Runnable轉(zhuǎn)換為Callable:

  public static <T> Callable<T> callable(Runnable task, T result) {
    if (task == null)
      throw new NullPointerException();
    return new RunnableAdapter<T>(task, result);
  }

FutureTask內(nèi)部包含一個Callable,并且可以接受Callable和Runnable作為構(gòu)造函數(shù):

  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) {
    this.callable = Executors.callable(runnable, result);
    this.state = NEW;    // ensure visibility of callable
  }

它的內(nèi)部就是調(diào)用了Executors.callable(runnable, result);方法進行轉(zhuǎn)換的。

以Runnable運行

既然是一個Runnable,那么FutureTask就可以以線程的方式執(zhí)行,我們來看一個例子:

@Test
  public void convertRunnableToCallable() throws ExecutionException, InterruptedException {
    FutureTask<Integer> futureTask = new FutureTask<>(new Callable<Integer>() {
      @Override
      public Integer call() throws Exception {
        log.info("inside callable future task ...");
        return 0;
      }
    });

    Thread thread= new Thread(futureTask);
    thread.start();
    log.info(futureTask.get().toString());
  }

上面例子是以單個線程來執(zhí)行的,同樣我們也可以將FutureTask提交給線程池來執(zhí)行:

  @Test
  public void workWithExecutorService() throws ExecutionException, InterruptedException {
    FutureTask<Integer> futureTask = new FutureTask<>(new Callable<Integer>() {
      @Override
      public Integer call() throws Exception {
        log.info("inside futureTask");
        return 1;
      }
    });
    ExecutorService executor = Executors.newCachedThreadPool();
    executor.submit(futureTask);
    executor.shutdown();
    log.info(futureTask.get().toString());
  }

看完上述內(nèi)容,是不是對Java FutureTask類的用法有進一步的了解,如果還想學(xué)習(xí)更多內(nèi)容,歡迎關(guān)注億速云行業(yè)資訊頻道。

向AI問一下細節(jié)

免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點不代表本網(wǎng)站立場,如果涉及侵權(quán)請聯(lián)系站長郵箱:is@yisu.com進行舉報,并提供相關(guān)證據(jù),一經(jīng)查實,將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI