移动构造函数和 std::move 混淆
move constructor and std::move confusion
我正在阅读有关std::move
,移动构造函数和移动赋值运算符的信息。老实说,我现在得到的只是困惑。现在我有一堂课:
class A{
public:
int key;
int value;
A(){key = 3; value = 4;}
//Simple move constructor
A(A&& B){ A.key = std::move(B.key);
A.value = std::move(B.value);}
};
- 我以为
B
是一个右值引用,为什么你可以std::move
应用于 ravlue 引用的成员? B.key
和B.value
被移动后,两者都无效,但作为类A
的对象如何B
失效?- 如果我有
A a(A())
,A()
显然是 rvlaue,A()
会被std::move
感动吗,为什么? 同样,如果我有一个函数
int add(int && z){ int x = std:move(z); int y = std:move(z); return x+y; }
如果我打电话给add(5)
,5
怎么能被移动,为什么?请注意,z
已经移动了两次,z
第一次移动后,它已经失效了,你怎么能再次移动它呢?
- 在定义
foo (T && Z )
(T
,Z
可以是任何东西(时,在定义的正文中,为什么我应该使用std::move(Z)
,因为Z
已经被右值引用传递了,什么时候应该使用std::move
?
std::move
不会移动任何内容,而是将其参数"标记"为右值引用。从技术上讲,它将类型转换为右值引用。然后,右值引用它由相应的移动构造函数或移动赋值运算符移动。对于仅包含具有简单移动 ctors/赋值运算符的成员的对象,移动 ctor/赋值运算符是微不足道的,只是复制。通常,对象的移动 ctor/赋值运算符调用其所有成员的移动 ctor/赋值运算符。
所以,每当你写
整数 x = 10;int y = std::move(x(;
在赋值y = std::move(x)
的右侧,您有一个类型为 int&&
的右值引用。但是,int
没有非平凡的移动ctor,并且简单地将右值复制到y
中,x
中没有任何变化。
另一方面
字符串 s = "某个字符串";字符串 moved_s = 标准::移动;在这里我们告诉编译器我们可以"窃取"s 的资源
是不同的。moved_s
的移动构造函数启动并"窃取"(即交换内部指针等(s
的资源,因为后者是右值引用。最后,s
将不包含任何元素。
-
B
是对象的名称。绑定引用后,它将命名一个对象。"右值引用"、"左值引用"和"命名对象"的区别仅适用于在您走到这一步之前如何绑定名称。
B.key
是对象中作为参数提供给此函数调用的变量的名称。
- "无效"不是搬家标准术语的一部分。标准库对象在移出后将处于未指定状态;但这不是这里发生的事情。
A.key = std::move(B.key)
行调用int
赋值的内置定义(这是简单的赋值,而不是函数调用(,这只是一个副本。所以B.key
保留了它的价值。
-
要进行
A(B())
编译,B
必须是尚未定义的类型名。(你是说A(A())
?如果是这样,那么答案是"是"(。 -
见2
-
每当您想要移出
Z.foo
而不是从Z.foo
复制
时,请使用
std::move(Z.foo)
。- 增量运算符与后缀混淆
- 瓦尔格林德:数学函数"Conditional jump or move depends on uninitialised value(s)"
- Usages of std::move
- 在C++中对T*类型执行std::move的意外行为
- C++图形类指针混淆
- OpenCV C++.快速计算混淆矩阵
- 关于std::move的使用,是否有编译警告
- 我应该实现右值推送功能吗?我应该使用std::move吗
- 通过实例理解std::move及其目的
- 使用仅使用一次的变量调用的复制构造函数.这可能是通过调用move构造函数进行编译器优化的情况吗
- 结构和双指针隐藏在其他结构中,多层混淆
- 混淆了如何使用IDL与Ethovision进行通信
- 是否可以在 C++03 中定义'move-and-swap idiom'等效项
- 关于 std::min, std::max 中的比较运算符的混淆
- 返回一个带有 std::move 的对象并链接函数
- 对单链表的混淆
- '[](std::list& list)<int>{return std::move(list)}(list)' 是否保证将 'list' 留空?
- CMake - 模块 + 库混淆
- 为什么字符串的 move() 会改变内存中底层数据的位置?
- 移动构造函数和 std::move 混淆