异步编程CompletableFuture
CompletableFuture
JDK 5引入了Future模式。Future接口是Java多线程Future模式的实现,在java.util.concurrent包中,可以来进行异步计算。
Future模式是多线程设计常用的一种设计模式。Future模式可以理解成:我有一个任务,提交给了Future,Future替我完成这个任务。期间我自己可以去做任何想做的事情。一段时间之后,我就便可以从Future那儿取出结果。
缺点:
- Future虽然可以实现获取异步执行结果的需求,但是它没有提供通知的机制,我们无法得知Future什么时候完成。
- 要么使用阻塞,在future.get()的地方等待future返回的结果,这时又变成同步操作。要么使用isDone()轮询地判断Future是否完成,这样会耗费CPU的资源。
CompletableFuture
- 能够将回调放到与任务不同的线程中执行,也能将回调作为继续执行的同步函数,在与任务相同的线程中执行。它避免了传统回调最大的问题,那就是能够将控制流分离到不同的事件处理器中。
- 弥补了Future模式的缺点。在异步的任务完成后,需要用其结果继续操作时,无需等待。可以直接通过thenAccept、thenApply、thenCompose等方式将前面异步处理的结果交给另外一个异步事件处理线程来处理。
- 可以使用指定的线程池处理任务,如果不指定使用默认线程池:ForkJoinPool线程池
CompletableFuture
JDK 5引入了Future模式。Future接口是Java多线程Future模式的实现,在java.util.concurrent包中,可以来进行异步计算。
Future模式是多线程设计常用的一种设计模式。Future模式可以理解成:我有一个任务,提交给了Future,Future替我完成这个任务。期间我自己可以去做任何想做的事情。一段时间之后,我就便可以从Future那儿取出结果。
缺点:
- Future虽然可以实现获取异步执行结果的需求,但是它没有提供通知的机制,我们无法得知Future什么时候完成。
- 要么使用阻塞,在future.get()的地方等待future返回的结果,这时又变成同步操作。要么使用isDone()轮询地判断Future是否完成,这样会耗费CPU的资源。
CompletableFuture
- 能够将回调放到与任务不同的线程中执行,也能将回调作为继续执行的同步函数,在与任务相同的线程中执行。它避免了传统回调最大的问题,那就是能够将控制流分离到不同的事件处理器中。
- 弥补了Future模式的缺点。在异步的任务完成后,需要用其结果继续操作时,无需等待。可以直接通过thenAccept、thenApply、thenCompose等方式将前面异步处理的结果交给另外一个异步事件处理线程来处理。
- 可以使用指定的线程池处理任务,如果不指定使用默认线程池:ForkJoinPool线程池
- xxx():表示该方法将继续在已有的线程中执行;
- xxxAsync():表示将异步在线程池中执行。
- thenAccept()处理正常结果;
- exceptional()处理异常结果;
- thenApplyAsync()用于串行化另一个CompletableFuture;
- anyOf()和allOf()用于并行化多个CompletableFuture。
优点:
- 异步任务结束时,会自动回调某个对象的方法;
- 异步任务出错时,会自动回调某个对象的方法;
- 主线程设置好回调后,不再关心异步任务的执行。
1、上一个异步操作结果影响下一个异步操作结果:ThenApplySync()
CompletableFuture<String> cfTask=CompletableFuture.supplyAsync(()->{}
CompletableFuture<Integer> cfTask2=cfTask.thenApplyAsync((code)->{}
cfTask2.thenAccept((price)->{}
2、前边任意一个异步有结果返回,直接进行下一步:anyOf()
CompletableFuture<String> cfTaskFrom1=CompletableFuture.supplyAsync(()->{}
CompletableFuture<String> cfTaskFrom2=CompletableFuture.supplyAsync(()->{}
CompletableFuture<Object cfTaskFrom=CompletableFuture.anyOf(cfTaskFrom1,cfTaskFrom2);
CompletableFuture<Integer> cfTaskResult=cfTaskFrom.thenApply((code)->{});
cfTaskResult.thenAccept((price)->{});
3、和anyOf()相反,allOf()需要所有任务全部完成才能继续下一步。
—Completable
本文作者:好名字
原文链接:http://www.cuizb.top/myblog/article/1638436164
版权声明: 本博客所有文章除特别声明外,均采用 CC BY 3.0 CN协议进行许可。转载请署名作者且注明文章出处。
本文来自博客园,作者:Java技术债务,转载请注明原文链接:https://www.cnblogs.com/cuizb/p/15635547.html