如何创建CompletableFuture实现void方法异步执行与c()触发逻辑
用CompletableFuture实现你的异步执行需求
你的思路完全正确!CompletableFuture.anyOf()确实是实现“a()或b()任意一个完成后执行c()”的最优方案之一,接下来我会一步步教你怎么创建对应的CompletableFuture对象,以及完整的实现代码。
第一步:创建执行a()和b()的CompletableFuture
因为你的a()和b()是无参数、无返回值的void方法,最适合用CompletableFuture.runAsync()方法来创建异步任务,它会自动把任务提交到默认的ForkJoin线程池(或者你指定的自定义线程池)中并发执行。
方式1:使用默认线程池
// 异步执行a(),返回对应的CompletableFuture CompletableFuture<Void> cf1 = CompletableFuture.runAsync(() -> a()); // 异步执行b(),返回对应的CompletableFuture CompletableFuture<Void> cf2 = CompletableFuture.runAsync(() -> b());
方式2:使用自定义线程池(生产环境推荐)
如果不想依赖默认线程池,你可以自己创建线程池来控制并发数,避免资源耗尽:
// 创建自定义线程池,比如固定2个线程的池 Executor customExecutor = Executors.newFixedThreadPool(2); // 用自定义线程池执行a()和b() CompletableFuture<Void> cf1 = CompletableFuture.runAsync(() -> a(), customExecutor); CompletableFuture<Void> cf2 = CompletableFuture.runAsync(() -> b(), customExecutor);
第二步:关联c()的执行逻辑
现在你有了cf1和cf2,接下来只需要用CompletableFuture.anyOf()监听这两个Future,只要其中任意一个完成,就触发c()的执行。这里有两种常见的实现方式:
方式1:异步触发c()(非阻塞,推荐)
这种方式不需要阻塞主线程,c()会在任意一个任务完成后自动异步执行:
// 监听cf1和cf2,任意一个完成后执行c() CompletableFuture.anyOf(cf1, cf2).thenRun(() -> c()); // 如果需要等待所有任务(a()、b()、c())都完成后再继续主线程,可以用allOf+join CompletableFuture<Void> cf3 = CompletableFuture.anyOf(cf1, cf2).thenRunAsync(() -> c()); CompletableFuture.allOf(cf1, cf2, cf3).join();
方式2:阻塞主线程后执行c()
如果你希望主线程等待任意一个任务完成后,再在主线程中执行c(),可以用join()阻塞:
// 阻塞主线程,直到cf1或cf2任意一个完成 CompletableFuture.anyOf(cf1, cf2).join(); // 此时执行c() c();
完整示例代码
把上面的逻辑整合起来,完整的Java代码示例如下:
import java.util.concurrent.CompletableFuture; import java.util.concurrent.Executor; import java.util.concurrent.Executors; public class AsyncExample { public static void a() { System.out.println("方法a开始执行,线程:" + Thread.currentThread().getName()); try { Thread.sleep(3000); // 模拟耗时操作 } catch (InterruptedException e) { Thread.currentThread().interrupt(); } System.out.println("方法a执行完成"); } public static void b() { System.out.println("方法b开始执行,线程:" + Thread.currentThread().getName()); try { Thread.sleep(5000); // 模拟耗时操作 } catch (InterruptedException e) { Thread.currentThread().interrupt(); } System.out.println("方法b执行完成"); } public static void c() { System.out.println("方法c开始执行,线程:" + Thread.currentThread().getName()); // 模拟c()的操作 System.out.println("方法c执行完成"); } public static void main(String[] args) { // 创建自定义线程池 Executor executor = Executors.newFixedThreadPool(2); // 创建异步任务 CompletableFuture<Void> cf1 = CompletableFuture.runAsync(AsyncExample::a, executor); CompletableFuture<Void> cf2 = CompletableFuture.runAsync(AsyncExample::b, executor); // 任意一个任务完成后执行c() CompletableFuture<Void> cf3 = CompletableFuture.anyOf(cf1, cf2).thenRunAsync(AsyncExample::c, executor); // 等待所有任务完成 CompletableFuture.allOf(cf1, cf2, cf3).join(); // 关闭线程池 ((java.util.concurrent.ThreadPoolExecutor) executor).shutdown(); System.out.println("所有任务执行完毕"); } }
运行这个示例你会看到,a()和b()会立刻并发执行,当a()完成后(因为它耗时更短),c()会马上开始执行,而b()会继续执行直到完成。
内容的提问来源于stack exchange,提问作者user5992911
相关产品推荐
相关产品推荐

