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

set_value

在 C++ 的 std::promisestd::future 机制中,set_value 是相对于 set_exception 的另一面。

如果说 set_exception 是用来报告“任务失败/出错了”,那么 set_value 就是用来提交“任务成功/结果算好了”

它是 std::promise 类的一个成员函数,作用是将计算结果存入共享状态,并通知对应的 future:“数据准备好了,可以来取了。”


1. set_value 的三种形态

根据 std::promise<T> 模板参数 T 的不同,set_value 的用法略有区别:

A. 传递具体数据 (std::promise<int>, std::promise<string> 等)

这是最直观的用法。子线程算出了结果,通过 set_value 传回去。

// 场景:子线程计算 10 + 20
void worker(std::promise<int> prom) {int result = 10 + 20;// 【关键动作】提交结果prom.set_value(result); 
}
// 主线程:fut.get() 将会得到 30

B. 仅发送完成信号 (std::promise<void>)

这是您在之前的代码片段中看到的用法。 如果 Tvoid,说明我们不关心返回值,只关心“任务做完了没有”

void worker(std::promise<void> prom) {// 做一些耗时操作...doHeavyWork();// 【关键动作】不传参数,仅表示“我做完了”prom.set_value(); 
}
// 主线程:fut.get() 只是解除阻塞,不返回任何数据

C. 传递引用 (std::promise<T&>)

较少见,用于直接传递对象的引用。


2. 完整工作流对比

我们可以把 std::promise 看作一个快递员

  • set_value: 快递员把货物(正常结果)放进了快递柜。
  • set_exception: 快递员把损坏说明书(异常对象)放进了快递柜。
  • future.get(): 收件人(主线程)打开快递柜。如果里面是货,就拿走;如果里面是说明书,当场崩溃(抛出异常)。

3. 代码示例:成功与失败的双岔路

这个例子展示了 set_valueset_exception 如何在一个逻辑分支中配合工作:

#include <iostream>
#include <thread>
#include <future>
#include <string>void dataLoader(std::promise<std::string> prom, bool success) {std::this_thread::sleep_for(std::chrono::seconds(1)); // 模拟耗时if (success) {// --- 情况 1:成功 ---// 使用 set_value 提交结果std::string data = "核心机密数据: 42";prom.set_value(data); } else {// --- 情况 2:失败 ---// 使用 set_exception 提交错误try {throw std::runtime_error("下载数据超时!");} catch (...) {prom.set_exception(std::current_exception());}}
}int main() {// 创建 promise 和 futurestd::promise<std::string> prom;std::future<std::string> fut = prom.get_future();// 启动线程 (尝试改为 false 看看效果)std::thread t(dataLoader, std::move(prom), true);std::cout << "主线程:正在等待数据..." << std::endl;try {// get() 会阻塞,直到 set_value 或 set_exception 被调用std::string result = fut.get(); std::cout << "主线程:收到数据 -> " << result << std::endl;} catch (const std::exception& e) {std::cout << "主线程:捕获异常 -> " << e.what() << std::endl;}t.join();return 0;
}

4. ⚠️ 重要注意事项:只能给一次

std::promise 的承诺是非常严肃的:你只能 set_value 或者 set_exception 一次。

如果你尝试在一个 promise 上调用两次设置(比如先 set_value 了一次,又 set_value 了一次),程序会抛出 std::future_error,错误码为 promise_already_satisfied

prom.set_value(10);
prom.set_value(20); // ❌ 崩溃!抛出 std::future_error

总结: set_value 是多线程通信中“报喜”的通道。配合之前的 set_exception(报忧),它们构成了 C++ std::future 机制完整的结果交付闭环

http://www.jsqmd.com/news/115926/

相关文章:

  • 日记1217
  • function的类型擦除
  • function bind
  • 日记12,19
  • Item10--令赋值操作符返回一个
  • Item9--绝不在构造和析构过程中调用虚函数
  • python django flask考研互助交流平台_c62p51fu--论文
  • 日记12.18
  • 离散化遍历
  • Ubuntu上使用VScode创建Maven项目
  • 线程(2)
  • 大规模语言模型的抽象思维与创新能力培养
  • 线程(1)
  • 方达炬〖发明超新技术〗:冰堆技术;冷极冰堆建筑技术;
  • Item6--若不想使用编译器自动生成的函数,就该明确拒绝
  • 我发现LLM解析基因数据优化抗癌药剂量,患者副作用直降40%
  • 日记12.16
  • 论文AIGC查重率高怎么办?6个降AI率工具和技巧,AI率从100%降到3%! - 还在做实验的师兄
  • PCL曲面重建——为一组点云重建凸多边形/凹多边形
  • 信息与关系:涌现的三大核心原则
  • Linux文件权限
  • 28
  • 灵遁者:量子基元理论带来的新观点
  • 【补充】远程连接学校服务器操作说明
  • 本地私有知识库新选择:访答软件真实体验分享
  • 划分dp
  • 花边服饰银发红眸者山间近景
  • 日记12,15
  • Item4--确定对象被使用前已先被初始化
  • string_view