关于std::vector移动语义的疑问:为何A的size变为0?
关于C++移动语义的疑问
示例代码
class Buck { public: Buck(std::vector<int> param) : data{param} {} std::vector<int> data; }; int main() { std::vector<int> A{1,2,3,4,5}; Buck b{std::move(A)}; std::cout << A.size() << std::endl; return 0; }
问题描述
这段代码输出为0,说明A的资源被转移到了b.data中。但按照理解:A通过std::move()转为右值,调用vector的移动构造函数把资源转移到构造函数参数param中,但param是构造函数内的左值,那data{param}为何能让A变成空容器?
解答
输出0的核心原因是资源转移发生在构造函数参数param的初始化阶段,而非data的初始化阶段,具体拆解三步流程:
std::move(A)将左值A强制转换为右值引用,作为实参传递给Buck的构造函数。
- 构造函数的形参
param是按值传递的,对于右值实参,std::vector会调用移动构造函数初始化param。这一步直接把A内部的堆内存资源转移给param,同时将A的内部状态置为空(所以A.size()变为0)。
- 构造函数的形参
- 初始化
data{param}时,param是构造函数内部的左值,此时调用的是std::vector的拷贝构造函数,将param的资源复制一份给data。但这一步对A的状态没有任何影响——因为A已经在第二步被掏空了。
- 初始化
简单来说:A的资源在param创建时就被移走了,后续data只是拷贝param的资源,和A早已无关。
内容的提问来源于stack exchange,提问作者user2276094
相关产品推荐
相关产品推荐

