I am trying to test RVO and rvalue reference. Here is the code:
#include <iostream>
using namespace std;
class B{
public:
int i;
B(){
i = 0;
cout << "B() " << i << endl;
}
B(const B& b){
i = 1;
cout << "B(const B&) " << i << endl;
}
B(const B&& b){//if remove this constructor, then call B(const B& b)
i = 2;
cout << "B(const B&&) " << i << endl;
}
~B(){
cout << "~B() " << i << endl;
}
};
B f(){
B b;
return b;
}
int main(){
B b = f();
return 0;
}
The output is:
B() 0
B(const B&&) 2
~B() 0
~B() 2
Environment: WIN8, Visual Studio 2012 Express
This means that the move constructor: B(const B&&) is called. Two issues raised:
- Why RVO is not applied here?
- Why NOT call the copy constructor: B(const B&)?
If I remove the B(const B&&), then B(const B&) is called. Weird output:
B() 0
B(const B&) 1
~B() 0
~B() 1
Here are references I found:
- Why g++ does not enable RVO here?
- RVO, move operations and a dilemma However, their scenarios are different from mine (RVO failure due to function parameter).
EDIT:
The move constructor should be B(B&&). The thing is why move constructor is called NOT the copy constructor.