鉴于课程:
class C
{
public:
C()
{
cout << "Dflt ctor.";
}
C(C& obj)
{
cout << "Copy ctor.";
}
C(C&& obj)
{
cout << "Move ctor.";
}
C& operator=(C& obj)
{
cout << "operator=";
return obj;
}
C& operator=(C&& obj)
{
cout << "Move operator=";
return obj;
}
};
然后在main:
int main(int argc, char* argv[])
{
C c;
C d = c;
C e;
e = c;
return 0;
}
正如您将从输出中看到的那样,复制ctor和operator=
的“常规”版本被调用,而不是那些带有rvalue args的版本。所以我想问一下,在什么情况下可以调用ctor和operator=(C&&)
?
答案 0 :(得分:7)
当右侧是临时的,或者使用C&&
或static_cast<C&&>
明确转换为std::move
的内容时,将调用移动构造函数。
C c;
C d(std::move(c)); // move constructor
C e(static_cast<C&&>(c)); // move constructor
C f;
f=std::move(c); // move assignment
f=static_cast<C&&>(c); // move assignment
C g((C())); // move construct from temporary (extra parens needed for parsing)
f=C(); // move assign from temporary
答案 1 :(得分:1)
C d = std::move(c)
来使用移动构造函数。
未经测试的示例,但可以更好地解释移动构造函数的使用:
C&& foo() { C c; return std::move(c); }
答案 2 :(得分:1)
std::swap(c,e); // c and e variables declared in your _tmain()
会调用move构造函数。
答案 3 :(得分:1)
所有变量都是左值,因此无法隐式移动,因为您可能需要稍后访问它们。另外,复制构造函数和赋值运算符采用const引用。
Rvalue引用可以处理rvalues,即临时对象。为了查看使用的移动构造函数,首先,您必须实际创建一个临时对象。此外,不要忘记RVO仍然适用,并且可能会修复任何或所有std :: cout呼叫。
您可以使用std :: move(左值)从左值创建右值。
答案 4 :(得分:-1)
使用移动运算符的更现实的例子是,如果你有一个静态类,它返回C&amp;&amp;在本地堆栈上创建如下:
static C&& CreateC()
{
C c();
//do something with your object
return c;
}
然后你这样调用它:
C x = CreateC(); // move operator is invoked here