UNIT 39 / 78 · W05-3
把共享状态放到明确的锁协议里
本单元预计 4 核心小时。可以分成多个学习时段,按完整小节推进;停下来时留下输入、命令、结果和下一步。
时间包含阅读、编码与检查,是学习预算而非期限。打开此页只保存阅读位置,不代表通过验收。
先知道自己在观察什么
线程、互斥锁与死锁 →
依次画 count 的互斥访问、join 完成关系与启动失败的 JoinAll;先做固定工作量。
先备不清楚时,沿章节入口补读;不要依赖翻过页数判断进度。
本单元另列的补授
以下时间加在原单元预算之外;完成对应读法后再进入依赖它的任务。
- 线程启动、joinable与emplace捕获 → · 30min
先留下自己的预测或独立尝试
预测四线程各1000次的4000;运行后检查异常注入回归仍完成,指出守卫与数据析构次序。
四个线程共享计数器 →源码下载与编译入口
下载到自己的练习目录。按本节给出的完整命令编译;多文件与driver要求见原任务。需要时查阅文件保存与编译操作 →
21-a.cpp先保存预测,再核对正文标明的预期或诊断。完整构建、多文件与设备实验按原任务命令执行。
通过一个变动看清原因
在副本把线程数组容量及JoinAll所引用的array类型一起从4改为2,并把共用increment循环从1000次改为500次;正常结果期望改为1000,注入路径partial期望改为500,保留两条路径和清理守卫。
修改后应观察到什么
正常路径计数1000;注入路径第一线程完成500次后被等待,partial=500;不能删除失败测试。
换一组条件,独立解决
独立写两个线程,每个局部计算 1+2+3+4 后在锁内一次合并;数据与锁活到 join 之后。
用这些条件检查自己的实现
- 每个局部值10,总数20;合并锁取得两次。
- 不在工作线程尚未完成时读结果;创建后续线程失败时已有线程仍会被等待。
用证据决定是否进入下一单元
- join 能否修复工作线程之间已经发生的 data race?
- 同一不变量的读操作需要遵守哪把锁?
本单元的验收依据
正常结果与失败清理可解释,拥有图显示数据比线程守卫更长寿;暂不要求通用分区算法。
留下自己的代码或推演、测试输入、真实输出和仍不确定的问题。未达到要求时,下一次继续本单元。