0

0

c++中的协程(coroutine)与线程的区别_c++并发模型选择【C++20】

冰火之心

冰火之心

发布时间:2025-12-07 15:50:40

|

902人浏览过

|

来源于php中文网

原创

协程是语言级轻量控制流机制,用于异步/生成器等场景;线程是OS级并发单元,负责真正并行。二者解决不同问题,需依任务性质协同使用。

c++中的协程(coroutine)与线程的区别_c++并发模型选择【c++20】

协程不是线程,也不是线程的替代品——它们解决的是不同层面的问题。C++20 引入的协程是**语言级的轻量级控制流机制**,用于简化异步、生成器、状态机等场景;而线程是操作系统调度的**并发执行单元**,负责真正意义上的并行。选错模型会导致性能浪费、逻辑混乱或根本无法编译。

协程:用户态的“可暂停函数”

协程本质是一个可以多次挂起(suspend)和恢复(resume)的函数。它不绑定 OS 线程,没有切换开销,也不需要内核参与调度。一次协程调用可能在同一个线程内分多段执行,中间穿插其他协程或普通代码。

  • 协程对象(如 std::coroutine_handle)只保存少量上下文(比如挂起点地址、局部变量地址),内存占用通常几十字节
  • 挂起/恢复由程序员通过 co_awaitco_yieldco_return 显式控制,行为完全可预测
  • 常见用途:异步 I/O 封装(避免回调地狱)、range 生成器(generator)、状态机建模(如协议解析)

线程:OS 管理的独立执行流

线程由操作系统创建和调度,拥有独立栈(默认 1MB+)、寄存器状态、优先级和调度策略。多个线程可在多核上真正并行运行,但也带来同步开销(锁、原子操作)、竞态风险和上下文切换成本(微秒级,但高频时显著)。

  • 适合 CPU 密集型任务(如图像处理、数值计算),或必须并行等待多个外部事件(如多路网络连接)
  • 不能直接用 co_await 等待线程结束——需配合 std::jthread 或条件变量,否则容易死锁
  • C++20 的 std::jthread 提供自动 join,但仍是重量级资源,不宜高频创建销毁

协同使用才是常态

实际项目中,协程与线程往往共存:用少量线程(如 IOCP 线程池或 epoll 循环线程)驱动大量协程。协程负责逻辑拆分,线程负责底层并行执行。

Sora
Sora

Sora是OpenAI发布的一种文生视频AI大模型,可以根据文本指令创建现实和富有想象力的场景。

下载

立即学习C++免费学习笔记(深入)”;

  • 例如:一个网络服务用 4 个线程跑 event loop,每个连接对应一个协程;协程遇到 socket read 就挂起,让出线程给其他协程,数据就绪后由 event loop 恢复它
  • 切忌在一个协程里调用阻塞 API(如 std::this_thread::sleep_for),这会卡住整个线程——应改用协程感知的定时器(如 asio::steady_timer
  • 协程内部可安全使用局部变量、引用、智能指针;但跨协程共享数据仍需线程安全措施(如 std::atomicstd::mutex

怎么选?看任务性质

判断依据不是“要不要并发”,而是“是否需要并行执行”以及“控制流是否天然分段”。

  • 需要同时跑多个 CPU 密集任务 → 用线程(或线程池)
  • 单线程里要处理上百个异步请求、且每个请求逻辑复杂 → 用协程 + event loop
  • 写一个返回迭代序列的函数(如遍历文件夹树)→ 用 generator 协程,比手写迭代器简洁得多
  • 既要并行又要异步 → 线程池 + 协程(如 boost::asio::thread_pool + co_await async_read

基本上就这些。协程不难学,但容易误当成“更轻的线程”来用;线程不难写,但滥用会导致扩展性瓶颈。C++20 协程不是银弹,它是帮你把“该串行的地方串行得更干净,该并行的地方并行得更可控”的工具

相关专题

更多
string转int
string转int

在编程中,我们经常会遇到需要将字符串(str)转换为整数(int)的情况。这可能是因为我们需要对字符串进行数值计算,或者需要将用户输入的字符串转换为整数进行处理。php中文网给大家带来了相关的教程以及文章,欢迎大家前来学习阅读。

318

2023.08.02

int占多少字节
int占多少字节

int占4个字节,意味着一个int变量可以存储范围在-2,147,483,648到2,147,483,647之间的整数值,在某些情况下也可能是2个字节或8个字节,int是一种常用的数据类型,用于表示整数,需要根据具体情况选择合适的数据类型,以确保程序的正确性和性能。本专题为大家提供相关的文章、下载、课程内容,供大家免费下载体验。

538

2024.08.29

c++怎么把double转成int
c++怎么把double转成int

本专题整合了 c++ double相关教程,阅读专题下面的文章了解更多详细内容。

53

2025.08.29

C++中int的含义
C++中int的含义

本专题整合了C++中int相关内容,阅读专题下面的文章了解更多详细内容。

197

2025.08.29

堆和栈的区别
堆和栈的区别

堆和栈的区别:1、内存分配方式不同;2、大小不同;3、数据访问方式不同;4、数据的生命周期。本专题为大家提供堆和栈的区别的相关的文章、下载、课程内容,供大家免费下载体验。

392

2023.07.18

堆和栈区别
堆和栈区别

堆(Heap)和栈(Stack)是计算机中两种常见的内存分配机制。它们在内存管理的方式、分配方式以及使用场景上有很大的区别。本文将详细介绍堆和栈的特点、区别以及各自的使用场景。php中文网给大家带来了相关的教程以及文章欢迎大家前来学习阅读。

572

2023.08.10

线程和进程的区别
线程和进程的区别

线程和进程的区别:线程是进程的一部分,用于实现并发和并行操作,而线程共享进程的资源,通信更方便快捷,切换开销较小。本专题为大家提供线程和进程区别相关的各种文章、以及下载和课程。

481

2023.08.10

PHP WebSocket 实时通信开发
PHP WebSocket 实时通信开发

本专题系统讲解 PHP 在实时通信与长连接场景中的应用实践,涵盖 WebSocket 协议原理、服务端连接管理、消息推送机制、心跳检测、断线重连以及与前端的实时交互实现。通过聊天系统、实时通知等案例,帮助开发者掌握 使用 PHP 构建实时通信与推送服务的完整开发流程,适用于即时消息与高互动性应用场景。

11

2026.01.19

微信聊天记录删除恢复导出教程汇总
微信聊天记录删除恢复导出教程汇总

本专题整合了微信聊天记录相关教程大全,阅读专题下面的文章了解更多详细内容。

73

2026.01.18

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
最新Python教程 从入门到精通
最新Python教程 从入门到精通

共4课时 | 5.8万人学习

Node.js 教程
Node.js 教程

共57课时 | 8.9万人学习

CSS3 教程
CSS3 教程

共18课时 | 4.7万人学习

关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送

Copyright 2014-2026 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号