You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

C++ erase/remove算法指针问题:埃氏筛法实现异常原因排查

故障原因分析

核心本质:lambda捕获规则 + 容器修改导致的取值异常

  • 第一段代码的逻辑是安全的:进入循环后立刻将*ptr的当前值(第一次循环就是2)拷贝到了局部变量p中,lambda通过值捕获拿到的是固定的p的副本,整个remove_if执行过程中判断条件永远是x % 固定值 == 0,所以可以正确移除对应质数的所有倍数。
  • 第二段代码的问题出在lambda的捕获逻辑:你在lambda中直接使用了*ptr,值捕获的时候只会捕获迭代器ptr本身,不会提前把*ptr的取值存下来。

具体执行流程错误推导(以第一次循环为例)

  1. 进入第一次while循环,ptr指向integers的首元素,取值为2
  2. 将2加入质数列表
  3. 执行remove_if,遍历vector判断元素是否要移除:
    • 第一个元素是2,满足2 % *ptr == 0,remove_if会将后续元素往前移动覆盖当前位置,此时ptr指向的位置的内容被改写为3
    • 后续判断其他元素时,*ptr的取值已经变成了3,判断条件偷偷变成了x % 3 == 0,自然不会再移除2的其他倍数(比如4、6、8等)
  4. 本次erase操作只会移除3的倍数,4就留在了integers中,下一轮循环就会被当作质数加入结果列表

补充说明

对std::vector执行remove_if、erase这类修改容器结构的操作时,所有旧迭代器都会失效,哪怕你提前拷贝了迭代器副本,访问其指向的内容也是未定义行为,可能出现取值错误、程序崩溃等各种异常结果。

内容的提问来源于stack exchange,提问作者hamster1230

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.06 18:27:05