示例:
package javaplay.thread.test;
import java.util.Random;
import java.util.concurrent.Callable;
import java.util.concurrent.CompletionService;
import java.util.concurrent.ExecutorCompletionService;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Future;
import java.util.concurrent.TimeUnit;
public class CallableAndFuture {
public static void main(String[] args) {
ExecutorService threadPool = Executors.newSingleThreadExecutor();
// 有返回结果的用submit 无返回结果的用execute
Future<String> future = threadPool.submit(new Callable<String>() {
@Override
public String call() throws Exception {
Thread.sleep(2000);
return "hello";
}
});
System.out.println("waiting result");
try {
// 超时就会抛异常
System.out.println("result : " + future.get(1, TimeUnit.SECONDS));
} catch (Exception e) {
e.printStackTrace();
}
threadPool.shutdown();// 必须关闭 否则就一直在那等待 消耗资源 优良的编码习惯
// CompletionService用于提交一组Callable任务,其take方法返回已完成的一个Callable任务对应的Future对象
// 即哪个任务先完成了,就先获得哪个任务的执行结果
ExecutorService threadPool2 = Executors.newFixedThreadPool(10);
CompletionService<Integer> completionService = new ExecutorCompletionService<>(threadPool2);
for (int i = 0; i < 10; i++) {// 提交10个任务
final int seq = i;
completionService.submit(new Callable<Integer>() {
@Override
public Integer call() throws Exception {
Thread.sleep(new Random().nextInt(5000));
return seq;
}
});
}
// 收获的季节
for (int i = 0; i < 10; i++) {
try {
System.out.println(completionService.take().get());
} catch (Exception e) {
e.printStackTrace();
}
}
threadPool2.shutdown();// 必须关闭
}
}
实际应用中,一个Future代表一个任务的运行结果,任务多时可用ArrayList<Future>来代表多个任务的运行结果,再循环获取;