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

C++存在移动构造且操作右值时仍调用拷贝构造的原因

问题1解答

std::vector扩容时需要满足强异常安全保证:如果扩容过程中出现异常,原有容器内的元素必须保持完整不被损坏。
你自定义的移动构造函数没有标记为noexcept,STL默认会认为该移动构造存在抛出异常的风险。如果此时调用移动构造迁移旧元素,一旦移动过程抛出异常,已经被移动的旧元素就处于失效状态,无法回滚到扩容前的状态,违反异常安全要求。所以vector会fallback到拷贝构造函数,对旧的存储10的对象执行深拷贝,保证原有元素不会被修改。

问题2解答

数值为20的对象是你刚构造的临时右值,属于本次push_back要插入的新元素,不需要参与旧空间已有元素的迁移流程。它只需要直接调用移动构造放到扩容后的新空间对应位置即可,不需要做深拷贝。

修复方案

只需要给移动构造加上noexcept声明,告诉STL该移动构造不会抛出异常,vector扩容时就会优先调用移动构造迁移旧元素,避免深拷贝:

Move(Move&& source) noexcept
    : data{ source.data }
{
    cout << "Move Constructor for "
        << *source.data << endl;
    source.data = nullptr;
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.30 05:54:00