天天看點

Callable、Future 和 FutureTask【享學堂】

Runnable 是一個接口,在它裡面隻聲明了一個 run()方法,由于 run()方法傳回值為 void

類型,是以在執行完任務之後無法傳回任何結果。

Callable 位于 java.util.concurrent 包下,它也是一個接口,在它裡面也隻聲明了一個方法,隻不過這個方法叫做

call(),這是一個泛型接口,call()函數傳回的類型就是傳遞進來的 V 類型。

Future 就是對于具體的 Runnable 或者 Callable 任務的執行結果進行取消、查詢是否完成、擷取結果。必要時可以通過

get 方法擷取執行結果,該方法會阻塞直到任務傳回結果。

因為 Future 隻是一個接口,是以是無法直接用來建立對象使用的,是以就有了下面的 FutureTask。
Callable、Future 和 FutureTask【享學堂】
FutureTask 類實作了 RunnableFuture 接口,RunnableFuture 繼承了 Runnable接口和 Future 接口,而 FutureTask 實作了 RunnableFuture 接口。是以它既可以作為 Runnable 被線程執行,又可以作為 Future 得到 Callable 的傳回值。
Callable、Future 和 FutureTask【享學堂】

是以我們通過一個線程運作 Callable,但是 Thread 不支援構造方法中傳遞Callable 的執行個體,是以我們需要通過 FutureTask 把一個 Callable 包裝成 Runnable,然後再通過這個 FutureTask 拿到 Callable 運作後的傳回值。

建立一個 FutureTask 的執行個體,有兩種方法

Callable、Future 和 FutureTask【享學堂】
public class CallableTest {

	public static class UserCallable implements Callable<Integer>{

		private int sum = 0;
		@Override
		public Integer call() throws Exception {
			int[] arr = IntStream.rangeClosed(1, 100).toArray();
			for (int i : arr) {
				sum += i;
			}
			return sum;
		}
	}
	//求1-100的和
	public static void main(String[] args) throws InterruptedException, ExecutionException {
		UserCallable userCallable = new UserCallable();
		FutureTask<Integer> futureTask = new FutureTask<>(userCallable);
		new Thread(futureTask).start();
		Integer sum = futureTask.get();
		System.out.println("sum = " + sum);
	}
}
           

繼續閱讀