When will the move ctor be invoked?
Given class:
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;
}
};
and then in main:
int main(int argc, char* argv[])
{
C c;
C d = c;
C e;
e = c;
return 0;
}
as you will see from the output the "regular" version of copy ctor and operator=
are invoked but not those with rvalue args. So I would like to as开发者_如何学编程k in what circumstances will the move ctor and operator=(C&&)
be invoked?
The move constructor will be invoked when the right-hand side is a temporary, or something that has been explicitly cast to C&&
either using static_cast<C&&>
or 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
IIRC, you have to use C d = std::move(c)
to use the move constructor.
An example not tested but that could explain better the use of move constructor :
C&& foo() { C c; return std::move(c); }
All of your variables are lvalues and thus cannot be moved implicitly, since you may need to access them later. In addition, copy constructors and assignment operators take const references.
Rvalue references work on, well, rvalues, that is, temporary objects. In order to see the move constructor used, first, you will have to actually create a temporary object. In addition, don't forget that RVO still applies and may well nail any or all of your std::cout calls.
You can create an rvalue from an lvalue using std::move(lvalue).
std::swap(c,e); // c and e variables declared in your _tmain()
would call the move constructor.
More realistic example of using move operator would be if you have a static class which returns C&& created on the local stack like this:
static C&& CreateC()
{
C c();
//do something with your object
return c;
}
and then you invoke it like this:
C x = CreateC(); // move operator is invoked here
精彩评论