当前位置: 首页 > news >正文

CompletableFuture多任务异步,获取返回值,汇总结果

线程池异步的基础知识

详情见:https://blog.csdn.net/sinat_32502451/article/details/133039624

线程池执行多任务,获取返回值

线程池的 submit()方法,可以提交任务,并返回 Future接口。
而 future.get(),可以获取到任务的结果,但是get()方法会阻塞,阻塞时间过长,会占用过多的系统资源。
因此在使用时,一般都会用 get(long timeout, TimeUnit unit) 设置超时时间。

//该线程池仅用于示例,实际建议使用自定义的线程池
ExecutorService executor = Executors.newCachedThreadPool();
Future<String> future = executor.submit(() -> "task1");
//阻塞,获取返回值,2秒超时
String result = future.get(2, TimeUnit.SECONDS);

不过,get(long timeout, TimeUnit unit) 比较适合设置单个任务的超时时间,在多任务的情况下,哪怕设置了超时时间,阻塞的时间也会特别长。
比如,有5个任务同时执行,每个任务设置2s的超时时间,在极端情况下,这些任务全部阻塞并超时,那总共要耗费的时间,可能会达到10s,这明显是不能接受的。
如果超时时间设置得太小,又可能出现频繁超时。在多任务获取返回值的场景,更适合使用 CompletableFuture。

CompletableFuture基础知识

详情见: https://blog.csdn.net/sinat_32502451/article/details/132819472

CompletableFuture多任务异步

CompletableFuture多任务异步,不需要返回值的话,主要使用 allOf()。

  • allOf():就是将多个任务汇总成一个任务,所有任务都完成时触发。allOf()可以配合get()一起使用。
public static void allOfTest() throws Exception {ExecutorService executorService = Executors.newCachedThreadPool();CompletableFuture<Void> cf1 = CompletableFuture.runAsync(() -> System.out.println("cf1 ok."), executorService);CompletableFuture<Void> cf2 = CompletableFuture.runAsync(() -> System.out.println("cf2 ok."), executorService);//将两个任务组装成一个新的任务,总共的超时时间为2sCompletableFuture.allOf(cf1, cf2).get(2, TimeUnit.SECONDS);}

CompletableFuture获取返回值

只有一个任务时,CompletableFuture的使用,跟线程池异步有点类似。
主要用到 CompletableFuture.supplyAsync(): 异步处理任务,有返回值。

     public static void supplyAsyncGet()  {//该线程池仅用于示例,实际建议使用自定义的线程池ExecutorService executorService = Executors.newCachedThreadPool();CompletableFuture<String> completableFuture = CompletableFuture.supplyAsync(()-> runTask(), executorService);String result = null;try {//获取返回值,2秒超时result = completableFuture.get(2, TimeUnit.SECONDS);} catch (Exception e) {logger.error("completableFuture.get error.", e);}logger.info("result:"+result);}private static String runTask() {try {//任务耗时。可以分别设置1000和3000,看未超时和超时的不同结果。Thread.sleep(1000);} catch (InterruptedException e) {logger.error("runTask error.", e);}return "taskResult";}

CompletableFuture多任务异步,获取返回值,汇总结果

有几个方法比较关键:

  • supplyAsync(): 异步处理任务,有返回值
  • whenComplete():任务完成后触发,该方法有返回值。还有两个参数,第一个参数是任务的返回值,第二个参数是异常。
  • allOf():就是所有任务都完成时触发。allOf()可以配合get()一起使用。

示例如下:

    /***  异步,多任务。汇总返回值*/public static void allOfGet()  {//该线程池仅用于示例,实际建议使用自定义的线程池ExecutorService executorService = Executors.newCachedThreadPool();//线程安全的list,适合写多读少的场景List<String> resultList = Collections.synchronizedList(new ArrayList<>(50));CompletableFuture<String> completableFuture1 = CompletableFuture.supplyAsync(() -> runTask("result1", 1000), executorService).whenComplete((result, throwable) -> {//任务完成时执行。用list存放任务的返回值if (result != null) {resultList.add(result);}//触发异常if (throwable != null) {logger.error("completableFuture1  error:{}", throwable);}});CompletableFuture<String> completableFuture2 = CompletableFuture.supplyAsync(() -> runTask("result2", 1500), executorService).whenComplete((result, throwable) ->{if (result != null) {resultList.add(result);}if (throwable != null) {logger.error("completableFuture2  error:{}", throwable);}});List<CompletableFuture<String>> futureList = new ArrayList<>();futureList.add(completableFuture1);futureList.add(completableFuture2);try  {//多个任务CompletableFuture[] futureArray = futureList.toArray(new CompletableFuture[0]);//将多个任务,汇总成一个任务,总共耗时不超时2秒CompletableFuture.allOf(futureArray).get(2, TimeUnit.SECONDS);} catch (Exception e) {logger.error("CompletableFuture.allOf Exception error.", e);}List<String> list = new ArrayList<>(resultList);list.forEach(System.out::println);}private static String runTask(String result, int millis) {try {//此处忽略实际的逻辑,用sleep代替//任务耗时。可以分别设置1000和3000,看未超时和超时的不同结果。Thread.sleep(millis);} catch (InterruptedException e) {logger.error("supplyAsyncGet error.");}return result;}

相关资料:

https://blog.csdn.net/sinat_32502451/article/details/132819472

相关文章:

CompletableFuture多任务异步,获取返回值,汇总结果

线程池异步的基础知识 详情见&#xff1a;https://blog.csdn.net/sinat_32502451/article/details/133039624 线程池执行多任务&#xff0c;获取返回值 线程池的 submit()方法&#xff0c;可以提交任务&#xff0c;并返回 Future接口。 而 future.get()&#xff0c;可以获取…...

Linux上Qt和Opencv人脸识别项目学习路线(嵌入式/C++)

本文将介绍Linux人脸识别项目的开发流程, 只作简略介绍所需知识点及大致流程。 注&#xff1a;若需详细教程请联系作者&#xff08;见文末&#xff09;。 一、基本开发环境搭建 1.1 安装虚拟机Ubuntu 虚拟机采用的是VMware&#xff0c;需要下载VMware安装包、ubuntu系统镜像…...

spring 源码阅读之@Configuration解析

Configuration解析 Configuration注解用于标识一个类是配置类&#xff0c;用于声明和组织Bean定义&#xff0c;首先Configuration本身也是一个Component&#xff0c;在其注解定义上标有Component Target(ElementType.TYPE) Retention(RetentionPolicy.RUNTIME) Documented Co…...

Java Web 33道面试题汇总

更多面试合集在:https://javaxiaobear.cn 1、http 的长连接和短连接? HTTP 协议有 HTTP/1.0 版本和 HTTP/1.1 版本。HTTP1.1 默认保持长连接(HTTP persistent connection,也翻译为持久连接),数据传输完成了保持 TCP 连接不断开(不发 RST 包、不四次握手),等待在同域名…...

设计模式记录

设计模式 抽象工厂模式单例模式要实现一个单例&#xff0c;需要关注的点有下面几个: 抽象工厂模式 PHP工厂模式是一种可扩展、可维护和可重复使用的方法&#xff0c;旨在提供通用接口&#xff0c;用于创建对象。工厂模式的主要组成部分包括抽象工厂、具体工厂、抽象产品和具体产…...

Java设计模式之亨元模式(Flyweight Pattern)

亨元模式&#xff08;Flyweight Pattern&#xff09;是一种结构型设计模式&#xff0c;旨在通过共享对象来最大限度地减少内存使用和提高性能。该模式适用于需要创建大量相似对象的情况&#xff0c;其中许多对象具有相同的状态。通过共享相同的状态&#xff0c;亨元模式可以减少…...

正点原子嵌入式linux驱动开发——Linux中断

不管是单片机裸机实验还是Linux下的驱动实验&#xff0c;中断都是频繁使用的功能&#xff0c;在裸机中使用中断需要做一大堆的工作&#xff0c;比如配置寄存器&#xff0c;使能IRQ等等。但是Linux内核提供了完善的中断框架&#xff0c;只需要申请中断&#xff0c;然后注册中断处…...

基于Jaya优化算法的电力系统最优潮流研究(Matlab代码实现)

&#x1f4a5;&#x1f4a5;&#x1f49e;&#x1f49e;欢迎来到本博客❤️❤️&#x1f4a5;&#x1f4a5; &#x1f3c6;博主优势&#xff1a;&#x1f31e;&#x1f31e;&#x1f31e;博客内容尽量做到思维缜密&#xff0c;逻辑清晰&#xff0c;为了方便读者。 ⛳️座右铭&a…...

Write-Ahead Log(PostgreSQL 14 Internals翻译版)

日志 如果发生停电、操作系统错误或数据库服务器崩溃等故障&#xff0c;RAM中的所有内容都将丢失&#xff1b;只有写入磁盘的数据才会被保留。要在故障后启动服务器&#xff0c;必须恢复数据一致性。如果磁盘本身已损坏&#xff0c;则必须通过备份恢复来解决相同的问题。 理论…...

CUDA 学习记录

1.关于volatile&#xff1a; 对于文章中这个函数&#xff0c; __global__ void reduceUnrollWarps8 (int *g_idata, int *g_odata, unsigned int n) {// set thread IDunsigned int tid threadIdx.x;unsigned int idx blockIdx.x * blockDim.x * 8 threadIdx.x;// convert…...

【Java 进阶篇】深入了解 Bootstrap 按钮和图标

按钮和图标在网页设计中扮演着重要的角色&#xff0c;它们是用户与网站或应用程序交互的关键元素之一。Bootstrap 是一个流行的前端框架&#xff0c;提供了丰富的按钮样式和图标库&#xff0c;使开发者能够轻松创建吸引人的界面。在本文中&#xff0c;我们将深入探讨 Bootstrap…...

基于Java的人事管理系统设计与实现(源码+lw+部署文档+讲解等)

文章目录 前言具体实现截图论文参考详细视频演示为什么选择我自己的网站自己的小程序&#xff08;小蔡coding&#xff09; 代码参考数据库参考源码获取 前言 &#x1f497;博主介绍&#xff1a;✌全网粉丝10W,CSDN特邀作者、博客专家、CSDN新星计划导师、全栈领域优质创作者&am…...

代码随想录算法训练营第五十九天| 647. 回文子串 516.最长回文子序列

今日学习的文章链接和视频链接 回文子串 https://programmercarl.com/0647.%E5%9B%9E%E6%96%87%E5%AD%90%E4%B8%B2.html 516.最长回文子序列 https://programmercarl.com/0516.%E6%9C%80%E9%95%BF%E5%9B%9E%E6%96%87%E5%AD%90%E5%BA%8F%E5%88%97.html 动态规划总结篇 https:…...

uniapp 小程序优惠劵样式

先看效果图 上代码 <view class"coupon"><view class"tickets" v-for"(item,index) in 10" :key"item"><view class"l-tickets"><view class"name">10元优惠劵</view><view cl…...

元梦之星内测上线,如何在B站打响声量?

元梦之星是腾讯天美工作室群研发的超开星乐园派对手游&#xff0c;于2023年1月17日通过审批。该游戏风格可爱软萌&#xff0c;带有社交属性&#xff0c;又是一款开黑聚会的手游&#xff0c;备受年轻人关注。 飞瓜数据&#xff08;B站版&#xff09;显示&#xff0c;元梦之星在…...

Python---循环---while循环

Python中的循环 包括 while循环与for循环&#xff0c;本文以while循环为主。 Python中所有的知识点&#xff0c;都是为了解决某个问题诞生的&#xff0c;就好比中文的汉字&#xff0c;每个汉字都是为了解决某种意思表达而诞生的。 1、什么是循环 现实生活中&#xff0c;也有…...

面试知识点--基础篇

文章目录 前言一、排序1. 冒泡排序2. 选择排序3. 插入排序4. 快速单边循环排序5. 快速双边循环排序6. 二分查找 二、集合1.List2.Map 前言 提示&#xff1a;以下是本篇文章正文内容&#xff0c;下面案例可供参考 一、排序 1. 冒泡排序 冒泡排序就是把小的元素往前调或者把大…...

FIFO设计16*8,verilog,源码和视频

名称&#xff1a;FIFO设计16*8&#xff0c;数据显示在数码管 软件&#xff1a;Quartus 语言&#xff1a;Verilog 代码功能&#xff1a; 使用verilog语言设计一个16*8的FIFO&#xff0c;深度16&#xff0c;宽度为8。可对FIFO进行写和读&#xff0c;并将FIFO读出的数据显示到…...

#力扣:2769. 找出最大的可达成数字@FDDLC

2769. 找出最大的可达成数字 - 力扣&#xff08;LeetCode&#xff09; 一、Java class Solution {public int theMaximumAchievableX(int num, int t) {return num 2*t;} }...

Juniper防火墙SSG-140 session 过高问题

1.SSG-140性能参数 2.问题截图 3.解决方法 &#xff08;1&#xff09;通过telnet 或 consol的方法登录到防火墙&#xff1b; &#xff08;2&#xff09;使用get session 查看总的session会话数&#xff0c;如果大于300 一般属于不正常情况 &#xff08;3&#xff09;使用get…...

未来机器人的大脑:如何用神经网络模拟器实现更智能的决策?

编辑&#xff1a;陈萍萍的公主一点人工一点智能 未来机器人的大脑&#xff1a;如何用神经网络模拟器实现更智能的决策&#xff1f;RWM通过双自回归机制有效解决了复合误差、部分可观测性和随机动力学等关键挑战&#xff0c;在不依赖领域特定归纳偏见的条件下实现了卓越的预测准…...

【Python】 -- 趣味代码 - 小恐龙游戏

文章目录 文章目录 00 小恐龙游戏程序设计框架代码结构和功能游戏流程总结01 小恐龙游戏程序设计02 百度网盘地址00 小恐龙游戏程序设计框架 这段代码是一个基于 Pygame 的简易跑酷游戏的完整实现,玩家控制一个角色(龙)躲避障碍物(仙人掌和乌鸦)。以下是代码的详细介绍:…...

Lombok 的 @Data 注解失效,未生成 getter/setter 方法引发的HTTP 406 错误

HTTP 状态码 406 (Not Acceptable) 和 500 (Internal Server Error) 是两类完全不同的错误&#xff0c;它们的含义、原因和解决方法都有显著区别。以下是详细对比&#xff1a; 1. HTTP 406 (Not Acceptable) 含义&#xff1a; 客户端请求的内容类型与服务器支持的内容类型不匹…...

Mybatis逆向工程,动态创建实体类、条件扩展类、Mapper接口、Mapper.xml映射文件

今天呢&#xff0c;博主的学习进度也是步入了Java Mybatis 框架&#xff0c;目前正在逐步杨帆旗航。 那么接下来就给大家出一期有关 Mybatis 逆向工程的教学&#xff0c;希望能对大家有所帮助&#xff0c;也特别欢迎大家指点不足之处&#xff0c;小生很乐意接受正确的建议&…...

django filter 统计数量 按属性去重

在Django中&#xff0c;如果你想要根据某个属性对查询集进行去重并统计数量&#xff0c;你可以使用values()方法配合annotate()方法来实现。这里有两种常见的方法来完成这个需求&#xff1a; 方法1&#xff1a;使用annotate()和Count 假设你有一个模型Item&#xff0c;并且你想…...

k8s业务程序联调工具-KtConnect

概述 原理 工具作用是建立了一个从本地到集群的单向VPN&#xff0c;根据VPN原理&#xff0c;打通两个内网必然需要借助一个公共中继节点&#xff0c;ktconnect工具巧妙的利用k8s原生的portforward能力&#xff0c;简化了建立连接的过程&#xff0c;apiserver间接起到了中继节…...

深入解析C++中的extern关键字:跨文件共享变量与函数的终极指南

&#x1f680; C extern 关键字深度解析&#xff1a;跨文件编程的终极指南 &#x1f4c5; 更新时间&#xff1a;2025年6月5日 &#x1f3f7;️ 标签&#xff1a;C | extern关键字 | 多文件编程 | 链接与声明 | 现代C 文章目录 前言&#x1f525;一、extern 是什么&#xff1f;&…...

css3笔记 (1) 自用

outline: none 用于移除元素获得焦点时默认的轮廓线 broder:0 用于移除边框 font-size&#xff1a;0 用于设置字体不显示 list-style: none 消除<li> 标签默认样式 margin: xx auto 版心居中 width:100% 通栏 vertical-align 作用于行内元素 / 表格单元格&#xff…...

如何在最短时间内提升打ctf(web)的水平?

刚刚刷完2遍 bugku 的 web 题&#xff0c;前来答题。 每个人对刷题理解是不同&#xff0c;有的人是看了writeup就等于刷了&#xff0c;有的人是收藏了writeup就等于刷了&#xff0c;有的人是跟着writeup做了一遍就等于刷了&#xff0c;还有的人是独立思考做了一遍就等于刷了。…...

LLMs 系列实操科普(1)

写在前面&#xff1a; 本期内容我们继续 Andrej Karpathy 的《How I use LLMs》讲座内容&#xff0c;原视频时长 ~130 分钟&#xff0c;以实操演示主流的一些 LLMs 的使用&#xff0c;由于涉及到实操&#xff0c;实际上并不适合以文字整理&#xff0c;但还是决定尽量整理一份笔…...