CompletableFuture优雅处理并发最佳实践

1、 supplyAsync方法需要一个Supplier函数接口,通常用于执行异步计算

CompletableFuture<String> future = CompletableFuture.supplyAsync(() -> {
    dosomething("处理事务");
    return "结果";
});

2、 runAsync接受一个Runnable函数接口,不关心异步任务的结果

CompletableFuture<Void> future = CompletableFuture.runAsync(() -> {
    dosomething("处理事务");
});

3、 组合使用

CompletableFuture<String> future1 = CompletableFuture.supplyAsync(() -> {
    simulateTask("task-1");
    return "task-1";
});

CompletableFuture<String> future2 = CompletableFuture.supplyAsync(() -> {
    simulateTask("task-2");
    return "task-2";
});

// 组合两个future,等待它们都完成
CompletableFuture<String> combinedFuture = future1.thenCombine(future2, (task-1, task-2) -> {
    return "==== " + task-1+ "," + task-2;
});

4、链式调用

  • thenApply用于处理和转换CompletableFuture的结果
  • thenAccept用于消费CompletableFuture的结果,不返回新的CompletableFuture
  • thenRun则不关心前一个任务的结果,只是在前一个任务执行完后,执行一些后续操作
CompletableFuture<String> future = CompletableFuture.supplyAsync(() -> {
    simulateTask("task-1");
    return "task-1";
});
future.thenApply(result -> {
    return "处理后的结果:" + result;
}).thenAccept(processedResult -> {
    System.out.println("最终结果:" + processedResult);
}).thenRun(() -> {
    System.out.println("所有操作完成");
});

5、 基本异常处理

CompletableFuture<String> future = CompletableFuture.supplyAsync(() -> {
    if (new Random().nextBoolean()) {
        throw new RuntimeException("出错啦!");
    }
    return "正常结果";
}).exceptionally(ex -> {
    return "错误:" + ex.getMessage();
});

future.thenAccept(System.out::println);

6、异常继续处理

CompletableFuture<String> future = CompletableFuture.supplyAsync(() -> {
    if (new Random().nextBoolean()) {
        throw new RuntimeException("出错啦!");
    }
    return "正常结果";
}).handle((result, ex) -> {
    if (ex != null) {
        return "处理异常:" + ex.getMessage();
    }
    return "处理结果:" + result;
});
future.thenAccept(System.out::println);

7、 依赖关系

CompletableFuture<String> masterFuture = CompletableFuture.supplyAsync(() -> {
    simulateTask("task-1");
    return "task-1";
});

CompletableFuture<String> dependentFuture = masterFuture.thenCompose(result -> {
    return CompletableFuture.supplyAsync(() -> {
        simulateTask("处理依赖于" + result + "的数据");
        return "处理后的数据";
    });
});

dependentFuture.thenAccept(System.out::println);

8、 处理多个Future

CompletableFuture<String> future1 = CompletableFuture.supplyAsync(() -> {
    simulateTask("任务一");
    return "结果一";
});

CompletableFuture<String> future2 = CompletableFuture.supplyAsync(() -> {
    simulateTask("任务二");
    return "结果二";
});

CompletableFuture<Void> allFutures = CompletableFuture.allOf(future1, future2);

allFutures.thenRun(() -> {
    System.out.println("所有任务完成");
});

CompletableFuture默认情况下使用ForkJoinPool,但在某些场景下使用自定义线程池可更好地控制资源

ExecutorService customExecutor = Executors.newFixedThreadPool(10);
CompletableFuture<String> future = CompletableFuture.supplyAsync(() -> {
    return "使用自定义线程池";
}, customExecutor);

当组合多个CompletableFuture,对每一个Future都进行错误处理,避免一个未捕获的异常破坏整个操作链

CompletableFuture<String> future1 = CompletableFuture.supplyAsync(() -> "任务1").exceptionally(ex -> "默认值1");
CompletableFuture<String> future2 = CompletableFuture.supplyAsync(() -> "任务2").exceptionally(ex -> "默认值2");
CompletableFuture<String> combinedFuture = future1.thenCombine(future2, (result1, result2) -> result1 + " 和 " + result2);
posted @ 2024-09-26 11:10  秋水秋色  阅读(221)  评论(0编辑  收藏  举报