async++库的使用示例
1、普通异步函数
如前面的博客介绍的,这个库中提供了async::spawn方法,这个方法通常用来启动异步函数,这个框架会利用线程池去完成函数,因此要注意数据安全。正因为将任务放到了单独的线程执行,并且还有调度开销,因此简单的任务最好不要使用这种方法,得不偿失。示例代码如下:
void demo_async1() {std::mutex mutex;auto task1 = async::spawn([&mutex]{{std::lock_guard<std::mutex> lock(mutex); std::cout << "this is in async thread" << std::endl;}return "hello world!!!"; }); while(!task1.ready()) {std::lock_guard<std::mutex> lock(mutex);std::cout << "this is in main thread" << std::endl;}task1.wait();// 这里会获取任务的返回值,即"hello world!!!"auto ret = task1.get();std::cout << ret << std::endl;
};
2、带有子任务的普通异步函数
async::spawn函数返回的仍然是一个任务,因此可以连续使用then来执行子任务,示例代码如下:
void demo_async2() {async::spawn([] {return "hello world";}).then([](const std::string& s) {return s;}).then([](async::task<std::string> task) {std::cout << task.get() << std::endl;});
}
有没有发现第一个子任务所执行的函数参数是std::string,而第二个子任务所执行的函数参数是async::taskstd::string task,而前面两个任务返回的都是字符串。这是因为异步编程中的 .then() 方法和 async::task 类型的处理方式有些特殊。在链式调用中,.then() 并不仅仅是一个普通的函数调用,它是用来接收一个异步任务完成后的结果,并且会返回一个新的异步任务。这意味着第一个子任务返回的并不是字符串,返回的字符串会被封装成async::taskstd::string,所以第二个子函数的参数类型必须是 async::taskstd::string。而主任务的返回值是std::string,所以第一个子任务的函数参数可以是std::string。
3、when_any和when_all的使用
when_any是任务集合中有一个任务完成就会返回,when_all是多有的任务完成才会返回。需要注意的是,when_any并不是第一个任务完成了就不执行其他的任务,其它的任务仍在执行,只不过when_any不会等他们执行完再返回。这里在测试的时候,如果测试when_all,一定要先注释when_any,否则程序会崩溃,原因就是task和shared_task的原因。它们返回的包含结果的数据结构都是std::tuple类型的,想取得结果要么使用辅助函数,要么使用std::get<0>(results).get()这种。不能使用for遍历,因为tuple的各元素大小可能不一样。也不可以使用std::get<first_result.index>,原因很简单,模版函数需要再编译时确定值,而不可以在运行时确定。
void demo_async3() {// 定义三个异步任务,分别模拟不同的执行时间auto task1 = async::spawn([] {std::this_thread::sleep_for(std::chrono::seconds(3)); // 模拟耗时任务std::cout << "Task 1 completed!" << std::endl;return 1;});auto task2 = async::spawn([] {std::this_thread::sleep_for(std::chrono::seconds(2)); // 模拟耗时任务std::cout << "Task 2 completed!" << std::endl;return 2;});auto task3 = async::spawn([] {std::this_thread::sleep_for(std::chrono::seconds(1)); // 模拟耗时任务std::cout << "Task 3 completed!" << std::endl;return 3;});// // 使用 when_any 等待最早完成的任务// auto any_result = async::when_any(task1, task2, task3);// any_result.wait(); // 等待第一个任务完成// auto first_result = any_result.get();// std::cout << "First completed task returned: " << first_result.index << std::endl;// 使用 when_all 等待所有任务完成auto all_result = async::when_all(task1, task2, task3);all_result.wait(); // 等待所有任务完成auto results = all_result.get();// 因为是Tuple,静态容器,每个元素的大小可能不一样,所以可以用这种方式访问// 如果是C++1,可以使用std::apply()来遍历tuplestd::cout << std::get<0>(results).get() << std::endl;std::cout << std::get<1>(results).get() << std::endl;std::cout << std::get<2>(results).get() << std::endl;
}
4、async::cancellation_token的使用
该异步框架提供了一个async::cancellation_token,它主要用来控制子任务的执行进度,是不是在主线程中取消子任务的执行,这样可以使得子线程中通过其控制子线程内部的执行进度,是不是取消(当然也可以做一些逻辑的控制)
void demo_async4() {async::cancellation_token c;auto t = async::spawn([&c] { std::cout << "-----line 68" << std::endl;async::interruption_point(c);while(!c.is_canceled());std::cout << "-----line 70" << std::endl;});sleep(1);std::cout << "-----line 79" << std::endl;c.cancel(); t.get();std::cout << "-----line 82" << std::endl;
}
5、事件任务的使用
我认为时间任务的主要作用是在主线程中控制子任务的执行时间点,并可以像子任务重设置参数。
void demo_async5() {async::event_task<int> e;auto t = e.get_task();// 这里只是将后面的任务放到了e的continuation_vectort.then([](int result) { std::cout << result << std::endl; });// 执行主任务,并将参数传给子任务,触发子任务e.set(42);
}
6、共享任务的使用
共享任务的优点是可以多次获取任务的结果,不像普通的任务那样,获取完结果,就会把内存释放掉。缺点是使用了引用计数,增加了资源消耗,但是现代计算机中,这些资源的消耗造成的影响较小,这里的代码必须加share(),根因和task类shared_task类的定义有关系,task类不允许拷贝,但是允许移动构造,但是shared_task都是可以的,模仿的std::future和std::shared_future的关系。
// 从测试代码中可以看出,我们可以利用共享任务,将其以参数的形式传到其它任务中
void demo_async6() {// 使用 async::spawn 创建异步任务并使用 .share() 方法共享auto t = async::spawn([] {std::cout << "Parent task" << std::endl;return 42; // 返回一些结果}).share();// 创建两个任务,它们共享 tauto task1 = async::spawn([t] {auto result = t.get(); // 获取共享任务的结果std::cout << "Task 1 result: " << result << std::endl;});auto task2 = async::spawn([t] {auto result = t.get(); // 获取共享任务的结果std::cout << "Task 2 result: " << result << std::endl;});// 等待任务完成task1.get();task2.get();
7、测试程序
直接贴代码
#include <iostream>
#include <mutex>
#include <ctime>
#include <unistd.h>
#include "../include/async++.h"
/*
上面的示例
*/
int main() {// demo_async1();// demo_async2();demo_async3();// demo_async4();//
相关文章:
async++库的使用示例
1、普通异步函数 如前面的博客介绍的,这个库中提供了async::spawn方法,这个方法通常用来启动异步函数,这个框架会利用线程池去完成函数,因此要注意数据安全。正因为将任务放到了单独的线程执行,并且还有调度开销&…...

springboot基于微信小程序的手机银行系统
Spring Boot基于微信小程序的手机银行系统是一种结合现代Web技术和移动应用优势的创新金融服务平台。 一、系统背景与意义 随着信息技术的快速发展和用户对便捷金融服务需求的日益增长,传统手机银行系统的人工管理方法已逐渐显露出效率低下、安全性低以及信息传输…...
25/1/22 算法笔记<ROS2> TF变换
TF(Transform) 是 ROS(Robot Operating System)中的一个核心功能,用于管理和发布坐标系之间的变换关系。TF 的主要作用是描述机器人系统中各个部分(如传感器、执行器、底盘等)之间的位置和姿态关…...

Android系统开发(六):从Linux到Android:模块化开发,GKI内核的硬核科普
引言: 今天我们聊聊Android生态中最“硬核”的话题:通用内核镜像(GKI)与内核模块接口(KMI)。这是内核碎片化终结者的秘密武器,解决了内核和供应商模块之间无尽的兼容性问题。为什么重要&#x…...
dp 凸优化
时间有点仓促,过几天会补。 来自 czz 学长的课,SMWC -> Day4 。 目录 凸函数介绍WQS二分1. P2619【国家集训队 2】Tree I2. CF739E Gosha is hunting 闵可夫斯基和1. QOJ-5421 Factories Once More2. GD 省集 tower Slope Trick1. CF713C2. ABC217H3.…...
详细介绍:Kubernetes(K8s)的技术架构(核心概念、调度和资源管理、安全性、持续集成与持续部署、网络和服务发现)
目录 前言1、K8s架构概述1.1、控制面(Control Plane)1.2、工作节点(Worker Node) 2、Kubernetes核心概念2.1、Pod2.2、ReplicaSet2.3、Deployment2.4、Service2.5、Namespace2.6、ConfigMap与Secret2.7、Persistent Volume&#x…...
[SAP ABAP] Dialog屏幕开发
Dialog屏幕开发在SAP ABAP环境中被广泛应用于创建交互式的用户界面,允许终端用户与应用程序进行互动 Dialog屏幕开发相关资料 [Dialog屏幕开发] 设置GUI Status 菜单/GUI Title 标题 [Dialog屏幕开发] 屏幕绘制(文本/输入框/按钮控件)...

安全测试之 SSTI 模板注入入门
文章目录 一、什么是SSTI?二、python 中的 Jinja2 漏洞验证三、Java 的 Thymeleaf 模版漏洞验证四、小结 一、什么是SSTI? SSTI(Server-Side Template Injection)是一种服务器端模板注入漏洞,它出现在使用模板引擎的W…...
滑动窗口解题模板
滑动窗口适用于固定长度的窗口问题,或者需要动态维护一个窗口的场景。 模板 public int slidingWindowTemplate(int[] nums, int k) { int n nums.length; int maxSum 0; // 记录最大值(或最小值) int windowSum 0; // 当前窗口的值 …...
SOC和SOH的含义
SOC 和 SOH 是在电池管理系统中常见的两个概念,通常用于描述电池的状态,以下是具体解释: SOC(State of Charge) 定义:荷电状态,也叫剩余电量,反映的是电池在一定条件下当前所剩余的…...

Genetic Prompt Search via Exploiting Language Model Probabilities
题目 利用语言模型概率的遗传提示搜索 论文地址:https://www.ijcai.org/proceedings/2023/0588.pdf 项目地址:https://github.com/zjjhit/gap3 摘要 针对大规模预训练语言模型(PLMs)的即时调优已经显示出显著的潜力,尤其是在诸如fewshot学习…...

1561. 你可以获得的最大硬币数目
class Solution:def maxCoins(self, piles: List[int]) -> int:piles.sort()res,n0,len(piles)for i in range(n//3):respiles[n-2-2*i]return res这里如果"你"想要获取最大,那么从最大的开始找 每隔俩算一个最大累计,Bob默认自己从最小那找…...

DNA结合之Motif_1:CNN
1,首先可以识别在KO前后的motif——》由CNN模型做出识别,看看这个有没有什么灵感 2,ZNF143等都可以使用来识别 3,暂时只使用单个peak文件,后期可以使用ENCODE中所有的对应的TF的peak文件 1,文件解压之后…...

kong 网关和spring cloud gateway网关性能测试对比
该测试只是简单在同一台机器设备对spring cloud gateway网关和kong网关进行对比,受限于笔者所拥有的资源,此处仅做简单评测。 一、使用spring boot 的auth-service作为服务提供者 该服务提供了一个/health接口,接口返回"OK"&…...

【2024 CSDN博客之星】个人收获分享
目录 [ C 语言 ] [ 数据结构 ] [ 算法 ] [ C ] [Linux] [Mysql] [Redis 文档学习] [Docker 云原生] [Git] [Qt] 转眼间大学就过了一年半,这一年半间好像习惯了,开心了那就学会吧,不开心了学会吧就开心了......期间在学习上面也走了…...
Codeforces Round 998 (Div. 3)(部分题解)
补题链接 A. Fibonacciness 思路:了解清楚题意,求得是最大的斐波那契的度,数组只有5个数(最多度为3),能列出其对应的式子 或 或 #include <bits/stdc.h> using namespace std; #define int long long void solve() {int …...
[创业之路-261]:《向流程设计要效率》-1-流程体系的建立是一场全方位的变革,一定会遇到各种阻力,需要全方位、系统性地进行流程管理
目录 一、思想和思维方式的转变 1.1 使能流程的战略 1.2 使能流程的组织 1. 流程决定组织 2. 基于流程分配责权利与资源 3. 从“管控”到“赋能” 1.3 使能流程的人才 1. 人才战略:从职能导向到流程导向 2. 能力模型:从职能专家到作战专家 3. …...
深入理解 Spring 的 Lazy Loading:原理、实现与应用场景
延迟加载(Lazy Loading)是 Spring 容器管理 Bean 的一种策略,指 只有在需要时(调用 getBean() 方法获取 Bean 时)才会实例化该 Bean。这是 Spring 提供的一种优化机制,用于提高启动效率和降低资源占用。 1.…...

扬帆数据结构算法之雅舟航程,漫步C++幽谷——LeetCode刷题之移除链表元素、反转链表、找中间节点、合并有序链表、链表的回文结构
人无完人,持之以恒,方能见真我!!! 共同进步!! 文章目录 一、移除链表元素思路一思路二 二、合并两个有序链表思路:优化: 三、反转链表思路一思路二 四、链表的中间节点思…...

【unity游戏开发之InputSystem——02】InputAction的使用介绍(基于unity6开发介绍)
文章目录 一、InputAction简介1、InputAction是什么?2、示例 二、InputAction参数相关1、点击齿轮1.1 Actions 动作(1)动作类型(Action Type)(2)初始状态检查(Initial State Check&a…...

stm32G473的flash模式是单bank还是双bank?
今天突然有人stm32G473的flash模式是单bank还是双bank?由于时间太久,我真忘记了。搜搜发现,还真有人和我一样。见下面的链接:https://shequ.stmicroelectronics.cn/forum.php?modviewthread&tid644563 根据STM32G4系列参考手…...

《Qt C++ 与 OpenCV:解锁视频播放程序设计的奥秘》
引言:探索视频播放程序设计之旅 在当今数字化时代,多媒体应用已渗透到我们生活的方方面面,从日常的视频娱乐到专业的视频监控、视频会议系统,视频播放程序作为多媒体应用的核心组成部分,扮演着至关重要的角色。无论是在个人电脑、移动设备还是智能电视等平台上,用户都期望…...

对WWDC 2025 Keynote 内容的预测
借助我们以往对苹果公司发展路径的深入研究经验,以及大语言模型的分析能力,我们系统梳理了多年来苹果 WWDC 主题演讲的规律。在 WWDC 2025 即将揭幕之际,我们让 ChatGPT 对今年的 Keynote 内容进行了一个初步预测,聊作存档。等到明…...
Matlab | matlab常用命令总结
常用命令 一、 基础操作与环境二、 矩阵与数组操作(核心)三、 绘图与可视化四、 编程与控制流五、 符号计算 (Symbolic Math Toolbox)六、 文件与数据 I/O七、 常用函数类别重要提示这是一份 MATLAB 常用命令和功能的总结,涵盖了基础操作、矩阵运算、绘图、编程和文件处理等…...

Mac下Android Studio扫描根目录卡死问题记录
环境信息 操作系统: macOS 15.5 (Apple M2芯片)Android Studio版本: Meerkat Feature Drop | 2024.3.2 Patch 1 (Build #AI-243.26053.27.2432.13536105, 2025年5月22日构建) 问题现象 在项目开发过程中,提示一个依赖外部头文件的cpp源文件需要同步,点…...
Python ROS2【机器人中间件框架】 简介
销量过万TEEIS德国护膝夏天用薄款 优惠券冠生园 百花蜂蜜428g 挤压瓶纯蜂蜜巨奇严选 鞋子除臭剂360ml 多芬身体磨砂膏280g健70%-75%酒精消毒棉片湿巾1418cm 80片/袋3袋大包清洁食品用消毒 优惠券AIMORNY52朵红玫瑰永生香皂花同城配送非鲜花七夕情人节生日礼物送女友 热卖妙洁棉…...

推荐 github 项目:GeminiImageApp(图片生成方向,可以做一定的素材)
推荐 github 项目:GeminiImageApp(图片生成方向,可以做一定的素材) 这个项目能干嘛? 使用 gemini 2.0 的 api 和 google 其他的 api 来做衍生处理 简化和优化了文生图和图生图的行为(我的最主要) 并且有一些目标检测和切割(我用不到) 视频和 imagefx 因为没 a…...
LangChain知识库管理后端接口:数据库操作详解—— 构建本地知识库系统的基础《二》
这段 Python 代码是一个完整的 知识库数据库操作模块,用于对本地知识库系统中的知识库进行增删改查(CRUD)操作。它基于 SQLAlchemy ORM 框架 和一个自定义的装饰器 with_session 实现数据库会话管理。 📘 一、整体功能概述 该模块…...

【笔记】WSL 中 Rust 安装与测试完整记录
#工作记录 WSL 中 Rust 安装与测试完整记录 1. 运行环境 系统:Ubuntu 24.04 LTS (WSL2)架构:x86_64 (GNU/Linux)Rust 版本:rustc 1.87.0 (2025-05-09)Cargo 版本:cargo 1.87.0 (2025-05-06) 2. 安装 Rust 2.1 使用 Rust 官方安…...
Oracle11g安装包
Oracle 11g安装包 适用于windows系统,64位 下载路径 oracle 11g 安装包...