Java異步調用Future對象


Future類存在於JDK的concurrent包中,主要用途是接收Java的異步線程計算返回的結果。

個人理解的使用場景大概如下:

有兩個任務A和B,A任務中僅僅需要使用B任務計算成果,有兩種方法實現:

  1. A和B在同一個線程中順序執行。即先執行B,得到返回結果之后再執行A。
  2. 開兩個線程,A和B並行執行。當A需要B的計算結果時如果B還沒有執行完,A既可以選擇阻塞等待B執行完,也可以先做其他的工作,過一段時間后再詢問一次B。

毫無疑問,如果B是一個耗時比較大的計算任務時,后者比前者的效率高了很多。

使用Java的Future對象的實現。

import java.util.Random;
import java.util.concurrent.Callable;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;

public class FutureDemo {
    
    public static void main(String[] args) {
        
        ExecutorService threadPool = Executors.newCachedThreadPool();
        Future<Integer> future = threadPool.submit(new Callable<Integer>() {  
            public Integer call() throws Exception {  
                Thread.sleep(3000);
                return new Random().nextInt(100);  
            }  
        }); 
        
        doSomething();
        
        try {  
            System.out.println("is B done : " + future.isDone());
            System.out.println("result of B : " + future.get());
            System.out.println("is B done : " + future.isDone());
            int result = future.get();
            
            doSomethingWithB(result);
        } 
        catch (InterruptedException e) {  
            e.printStackTrace();  
        } 
        catch (ExecutionException e) {  
            e.printStackTrace();  
        } 
        System.exit(0);
    }

    private static void doSomethingWithB(int result) {
        // TODO Auto-generated method stub
        
    }

    private static void doSomething() {
        // TODO Auto-generated method stub
        
    }

}

輸出結果:

is B done : false
result of B : 25
is B done : true

Future對象使用get方法獲取線程的返回值,即call方法的返回值。

不帶參數的get方法是阻塞方法,只要線程為返回結果就會一直阻塞直到有結果為止。

可以使用isDone方法判斷線程是否結束。也可以使用帶參數的get方法,若指定時間內還沒有得到線程返回值,會拋出TimeoutException的異常。

該方法源碼:

/**
     * Waits if necessary for at most the given time for the computation
     * to complete, and then retrieves its result, if available.
     *
     * @param timeout the maximum time to wait
     * @param unit the time unit of the timeout argument
     * @return the computed result
     * @throws CancellationException if the computation was cancelled
     * @throws ExecutionException if the computation threw an
     * exception
     * @throws InterruptedException if the current thread was interrupted
     * while waiting
     * @throws TimeoutException if the wait timed out
     */
    V get(long timeout, TimeUnit unit)
        throws InterruptedException, ExecutionException, TimeoutException;

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM