检查异步操作的不同完成顺序
Review both overlapping completion orders
组合测试共享状态上的竞争操作,避免只分别检查每个操作。
以下示例与示意结果由本站编写,用于说明方法,不是模型实测结果。
使用场景
编辑器延迟刷新取回旧文档v1,保存已写新文档v2;两项操作都更新同一状态。分别检查它们各自赋值正确,不能排除旧刷新覆盖新保存。
具体做法
声明调用边界与不变量“旧刷新不得覆盖较新保存”。画刷新/保存/共享状态合并时序,在相关await前后设受控暂停。先保存完成再释放刷新,由新消费者读取;再测刷新完成后保存。核版本检查或取消实际阻止哪个时序,不以原子赋值或单线程作顺序证明。保留每条观察与预期。
反例
两函数赋值是原子的,分别测试通过便宣称无竞态,不组合交错。
改进写法
暂停v1刷新应用,先完成v2保存再放行刷新,最终新读取必须v2;再测相反顺序。记录版本/取消门禁及受控关卡结果,若任一顺序不可能,引用具体阻止机制。
为什么这样改
跨await允许竞争动作穿插,单次赋值原子不保护跨操作的新鲜度。组合时序和新读取暴露旧结果覆盖,而不是仅看操作返回。
如何验证
教学无门禁:保存v2后刷新v1,最终v1违反不变量;版本拒绝旧结果后应v2。相反顺序也最终v2。未运行只是预期轨迹;测试应确认等待关卡而非猜测延时。
适用边界
两顺序覆盖相关交错,不是所有并发安全证明。外部持久化、取消有效性与多文档身份还需契约;有例外应明确授权条款,不能以损害有限代替满足要求。