在 C++ 中,std::future 和 std::async 是 C++11 标准 并发库的一部分。它们允许您异步/Asynchronous运行任务并在稍后获取结果,非常适合编写非阻塞代码和并行化计算。以下是它们的工作原理和典型用法。
C++ std::async
std::async 是一个高级函数,允许您异步启动一个任务(一个可调用对象,如函数或 lambda)。您指定要运行的函数,std::async 返回一个表示该 函数结果的 std::future。您可以稍后获取该结果,无论是任务完成时还是您需要时。
#include <iostream>
#include <future>
#include <chrono>
int compute() {
std::this_thread::sleep_for(std::chrono::seconds(2)); // 模拟工作
return 42; // 计算结果
}
int main() {
// 异步启动任务
std::future<int> result = std::async(std::launch::async, compute);
// 当 compute() 运行时执行其他任务...
// 获取 compute() 的结果(如果任务未完成则会等待)
int value = result.get();
std::cout << "结果: " << value << std::endl;
return 0;
}
在此示例中:
- std::async(std::launch::async, compute) 异步启动 compute(),返回一个 std::future 对象。
- result.get() 调用等待任务完成(如果尚未完成)然后获取结果。
C++ std::launch 策略
- std::launch::async: 强制任务在新线程上异步运行。
- std::launch::deferred: 推迟执行直到 future 上调用 get() 或 wait(),使其同步运行。
如果省略策略,C++ 可能根据实现定义的标准选择其中之一。
C++ std::future
std::future 是一个类模板,表示稍后获取的结果。它本质上是一个异步操作结果的占位符。
关键方法
- get(): 如果结果尚未完成则等待并获取结果。调用 get() 后,std::future 变为空。
- wait(): 等待任务完成,但不获取结果。
- valid(): 如果 std::future 具有共享状态(即有结果可用)返回 true。
- wait_for() 和 wait_until(): 等待特定时间或直到结果可用的截止时间。
带有 wait_for 的示例
if (result.wait_for(std::chrono::seconds(1)) == std::future_status::ready) {
std::cout << "结果已就绪: " << result.get() << std::endl;
} else {
std::cout << "仍在等待结果..." << std::endl;
}
此代码检查结果是否在 1 秒内就绪。如果没有就绪则继续执行,不 阻塞。
C++ std::promise
对于更高级的用法,std::promise 允许您手动设置 std::future 的结果。std::promise 对象提供一个 std::future,您可以显式设置结果。
#include <iostream>
#include <future>
#include <thread>
void setPromise(std::promise<int> p) {
p.set_value(10); // 设置 promise 的结果
}
int main() {
std::promise<int> p;
std::future<int> f = p.get_future(); // 从 promise 获取 future
std::thread t(setPromise, std::move(p)); // 将 promise 传递给线程
t.join();
std::cout << "promise 的结果: " << f.get() << std::endl; // 获取结果
return 0;
}
在此例子中,结果 10 是由 std::promise 设置的,std::future 可以通过 f.get() 获取。
C++ Future/Async/Promise 总结
- std::async: 启动一个异步运行的任务,返回一个 std::future。
- std::future: 表示将来会设置的值,通常是异步任务的返回值。
- std::promise: 允许手动设置 std::future 的结果。
使用这些功能,您可以有效地管理 C++ 中的异步任务,更轻松地并行运行计算或将工作分配给其他线程而不阻塞主线程。
英文:Tutorial on C++ Future, Async and Promise
C/C++编程
- 理解C++中的std::transform_reduce及示例
- 使用原子 TAS 指令实现自旋锁
- C++中检测编译时与运行时: if consteval 与 std::is_constant_evaluated()
- C++ 转发引用: 完美转发的关键
- 理解 C++ 中的 dynamic_cast: 安全的向下转型与向上转型
- C与C++: restrict关键字及其在编译器优化中的作用
- C++的左值/lvalue, 右值/rvalue和右值引用/rvalue references
- C++中的assert和static_assert的区别
- C++: auto_ptr智能指针被弃用
- C++中的consteval是什么? 它与const和constexpr有何不同?
- C++ 教程: 用std::move来移动所有权
- C++中的 const和constexpr 比较
- 简易教程: C++的智能指针
- C++ 编程练习题: 如何合并两个二叉树?
- C++ 编程练习题 - 找出第三大的数
- C++ 编程练习题 - 最多连续的 1
- C++ 编程练习题 - 左子树叶节点之和 (深度优先+广度优先+递归)
- C++ 编程练习题 - 最多水容器 (递归)
- C++的异步编程: std::future, std::async 和 std::promise
- C编程练习题: 翻转整数位
- C++编程练习题: 找出字符串的所有大小小组合
- C/C++ 中的内存管理器(堆与栈)
- C++编程练习题: 对两单向链表求和
强烈推荐
- 英国代购-畅购英伦
- TopCashBack 返现 (英国购物必备, 积少成多, 我2年来一共得了3000多英镑)
- Quidco 返现 (也是很不错的英国返现网站, 返现率高)
- 注册就送10美元, 免费使用2个月的 DigitalOcean 云主机(性价比超高, 每月只需5美元)
- 注册就送10美元, 免费使用4个月的 Vultr 云主机(性价比超高, 每月只需2.5美元)
- 注册就送10美元, 免费使用2个月的 阿里 云主机(性价比超高, 每月只需4.5美元)
- 注册就送20美元, 免费使用4个月的 Linode 云主机(性价比超高, 每月只需5美元) (折扣码: PodCastInit2022)
- PlusNet 英国光纤(超快, 超划算! 用户名 doctorlai)
- 刷了美国运通信用卡一年得到的积分 换了 485英镑
- 注册就送50英镑 – 英国最便宜最划算的电气提供商
- 能把比特币莱特币变现的银行卡! 不需要手续费就可以把虚拟货币法币兑换
微信公众号: 小赖子的英国生活和资讯 JustYYUK