我正在试验来自JDK8的JDK8 API,从它中尝试acceptEither()方法。请看下面的代码(然后我将提出我的关切):
public class AcceptEither {
public static void main(String[] args) {
CompletableFuture<Double> completableFuture2
= CompletableFuture.supplyAsync(TaskSupplier::getSomeArbitraryDouble);
CompletableFuture<Double> completableFuture3
= CompletableFuture.supplyAsync(TaskSupplier::getAnotherArbitraryDouble);
CompletableFuture<Void>completableFutureForAcptEither
= completableFuture2.acceptEither(completableFuture3, (val)-> {
System.out.println("val: "+val);
});
/*while(true){
if(completableFutureForAcptEither.isDone())
break;
System.out.println("task did not complete");
}
System.out.println("task finally completed");*/
System.out.println("exiting main method");
}
}
class TaskSupplier{
static double getSomeArbitraryDouble(){
try {
Thread.sleep(5000L);
} catch (InterruptedException e) {
e.printStackTrace();
}
return 5;
}
static double getAnotherArbitraryDouble(){
try {
Thread.sleep(3000L);
} catch (InterruptedException e) {
e.printStackTrace();
}
return 10;
}
}请注意注释无限的时间循环!在这种情况下,输出如下:
exiting main method我们可以看到,由CompletableFuture返回的acceptEither()无法执行提供的action。
但是,如果我不注释无限时间循环,则会得到以下输出:
task did not complete
task did not complete
task did not complete
val: 10.0
task did not complete
task did not complete
task did not complete
task did not complete
task finally completed
exiting main method以下是acceptEither方法的文档:
public CompletableFuture<Void> acceptEither(CompletionStage<? extends T> other,
Consumer<? super T> action)
Description copied from interface: CompletionStage
Returns a new CompletionStage that, when either this or the other given stage complete normally, is executed with the corresponding result as argument to the supplied action. See the CompletionStage documentation for rules covering exceptional completion.很明显,这一次由acceptEither()返回的acceptEither()被执行。
在这些观察之后,我可以看到执行action的主线程(运行main方法)和线程(来自Following )之间的一些依赖关系。
我觉得在池线程执行提供的action之前,主线程不应该到达其生命的尽头!但我一点也不确定这个推论。请告诉我这里发生了什么事。
发布于 2016-01-16 12:11:19
主线程不等待中的任务。公共池的文档说:
然而,这个池和任何正在进行的处理都会在程序System.exit(int)上自动终止。任何在程序终止前依赖异步任务处理来完成的程序都应该在退出之前调用commonPool().awaitQuiescence。
您还可以使用CompletableFuture的其他方法来使用自己的执行器,这些方法接受签名中的执行者。这样,所有提交的任务都将在执行器上执行。
ExecutorService executor = Executors.newCachedThreadPool();
CompletableFuture.supplyAsync( () -> {...}, executor);
...然后关闭主线程末尾的执行器。
executor.shutdown();https://stackoverflow.com/questions/34826727
复制相似问题