使用CompletableFuture实现多个异步任务并行完成后合并结果
业务场景
需要同时从多个副本数据库中查询数据,并对查询结果进行合并去重处理后返回前端。
实现过程涉及多数据源切换,这里不作过多讨论。
编码实现
实现过程:
1、定义异步查询数据方法;
2、通过CompletableFuture的allOf方法对多个异步执行结果进行处理;
public class CompletableFutureTests {
@Autowired
private UserDao userDao;
@Test
public void testSomeTaskAndJoin() throws Exception {
// DynamicDataSourceContextHolder.dataSourceIds根据动态数据源数量
// 异步执行每个数据源查询方法
// 返回一个Future集合
List<CompletableFuture<List<User>>> futures = DynamicDataSourceContextHolder.dataSourceIds.stream()
.map(this::queryUsers).collect(Collectors.toList());
// 多个异步执行结果合并到该集合
List<User> futureUsers = new ArrayList<>();
// 通过allOf对多个异步执行结果进行处理
CompletableFuture allFuture = CompletableFuture.allOf(futures.toArray(new CompletableFuture[futures.size()]))
.whenComplete((v, t) -> {
// 所有CompletableFuture执行完成后进行遍历
futures.forEach(future -> {
synchronized (this) {
// 查询结果合并
futureUsers.addAll(future.getNow(null));
}
});
});
// 阻塞等待所有CompletableFuture执行完成
allFuture.get();
// 对合并后的结果集进行去重处理
List<User> result = futureUsers.stream().distinct().collect(Collectors.toList());
log.info(result.toString());
}
/**
* 用户异步查询方法
* @param datasourceKey 动态数据源Key
* @return
*/
public CompletableFuture<List<User>> queryUsers(String datasourceKey) {
// 定义异步查询Future对象
CompletableFuture<List<User>> queryFuture = CompletableFuture.supplyAsync(() -> {
// 切换数据源
DynamicDataSourceContextHolder.setDataSourceRouterKey(datasourceKey);
// 执行ORM查询方法
return userDao.selectAll();
});
// 异步完成执行方法
queryFuture.whenCompleteAsync(new BiConsumer<List<User>, Throwable>() {
@Override
public void accept(List<User> users, Throwable throwable) {
// 这里主要记录异步执行结果
log.info("数据源[{}]查询完成,查询记录[{}]条", datasourceKey, users.size());
}
});
// 返回future对象
return queryFuture;
}
}
使用CompletableFuture实现多个异步任务并行完成后合并结果的更多相关文章
- 【原】iOS多线程之异步任务+并行队列情况与异步任务+串行队列(主队列)情况
异步任务+并行队列 把异步任务放到并行队列进行执行,异步任务会在不同的线程中执行. /*异步执行+并行队列*/ - (IBAction)clickBasic1:(UIButton *)sender { ...
- F# 天生就是就异步和并行的料
做模型开发免不了要使用异步和并行计算,尤其在多核CPU的今天,更是如此,F#恰逢其时,天生就具备这种能力,先看一个例子. open System open System.Drawing open Sy ...
- iOS:转载:同步、异步、并行、串行的详解
理解 iOS 开发中 GCD 相关的同步(synchronization)\ 异步(asynchronization),串行(serial)\ 并行(concurrency)概念 2014年11月21 ...
- swoolefy PHP的异步、并行、高性能网络通信引擎内置了Http/WebSocket服务器端/客户端
近半年来努力付出,项目终于要正式结项了,团队4人经历了很多困难,加班加点,最终完成了!剩下的时间将总结一下在该项目中用到知识和遇到问题.今天就从swoole说起!项目中实现异步大文件传输的功能,在服务 ...
- 关于使用Iscroll.js异步加载数据后不能滑动到最底端的问题解决方案
关于使用Iscroll.js异步加载数据后不能滑动到最底端,拉到最下边又弹回去的问题困扰了我老半天,相信很多朋友都遇到了.我刚好不小心解决了,和大家分享一下.由于各种忙,下边就直接上代码吧. (前提是 ...
- 要求两个异步任务都完成后, 才能回到主线程:dispatch_group_t
需求:两个异步任务都完成后, 回到主线程 /** 1.下载图片1和图片2 2.将图片1和图片2合并成一张图片后显示到imageView上 思考: * 下载图片 : 子线程 * 等2张图片都下载完毕后, ...
- C# 【一】进程 , 线程 , 微线程 , 同步 , 异步 , 并发 , 并行 , 阻塞 , 非阻塞
一 理解篇 前言 本文仅仅用作借鉴使用,作者刚入行不久,所以请不小心看到这篇文章的朋友,手下留情. 本文以小故事的形式进行叙述,逻辑不通之处.请理解. 如有错误 ,欢迎指出. 谢谢. ...
- iOS:对GCD中 同步、异步、并行、串行的见解
1.GCD-同步执行多线程时 GCD中不管向什么类型的队列加同步任务,实际上都会加到当前线程中(一般为主线程). 2.GCD-异步执行多线程时 GCD中不管向什么类 ...
- 通过一个示例形象地理解C# async await 非并行异步、并行异步、并行异步的并发量控制
前言 接上一篇 通过一个示例形象地理解C# async await异步 我在 .NET与大数据 中吐槽前同事在双层循环体中(肯定是单线程了)频繁请求es,导致接口的总耗时很长.这不能怪前同事,确实难写 ...
- 异步与并行~List<T>是线程安全的吗?
返回目录 题目有点意思,大家都知道Dictionary<K,V>不是线程安全的类型,而List<T>是线程安全的吗?在今天之前大叔没有去测试过,而就在今天也是一个VIP问我,说 ...
随机推荐
- centos7.X安装mysql5.7 – 东凭渭水流
1.下载mysql5.7 可以使用windows下载好后上传至Linux.网络条件好的推荐使用 wget https://dev.mysql.com/get/Downloads/MySQL-5.7/m ...
- Pytorch构建超分辨率模型——常用模块
Import required libraries: import torch import torch.nn as nn import torch.optim as optim from torch ...
- 浅谈API安全的应用
理论基础 API它的全称是Application Programming Interface,也叫做应用程序接口,它定义了软件之间的数据交互方式.功能类型.随着互联网的普及和发展,API 从早期的 ...
- Docker部署cas
一.首先安装cas镜像 1.拉取cas docker镜像 docker pull apereo/cas 2.启动容器: docker run --name cas -p 8443:8443 -p 8 ...
- cephadm快速部署指定版本ceph集群及生产问题处理
cephadm快速部署指定版本ceph集群及生产问题处理 目录 cephadm快速部署指定版本ceph集群及生产问题处理 1.虚拟机规划:centos8 2.ceph版本:(安装指定版本在源里面指定即 ...
- MySQL数据库触发器讲解 [创建/删除/查询/select into]
刚学习实例完mysql触发器, 前来分享学习经验. 菜鸟装逼, 老鸟勿喷 先来认识一下有关触发器的一些关键词. 在使用触发器时, 这些关键词将被用到, 请记下它们的模样和用途(意思) cre ...
- Building-Mobile-Apps-with-Ionic-2中文翻译工作
最近没啥工作量, 然后学完了这本书, 接着又茫然找不到该干啥, 所以想着何不翻译这个书呢. 这本书首先给我们普及了Ionic 2的基础知识, Ionic 2和Ionic 1有本质上的区别, Ionic ...
- PackageManager
/* * Copyright (C) 2006 The Android Open Source Project * * Licensed under the Apache License, Versi ...
- DHCP和PXE是怎么工作的
dhcp(Dynamic Host Configuration Protocol):配置一段共享IP地址,为新上线的机器分配IP地址,回收下线机器的IP地址. 正常情况下主机(DHCP client) ...
- 手把手教你写一个JSON在线解析的前端网站1
前言 作为一名Android开发,经常要跟后端同事联调接口,那么总避免不了要格式化接口返回值,将其转换为清晰直观高亮的UI样式以及折叠部分内容,方便我们查看定位关键的信息. 一直以来都是打开Googl ...