Reputation: 3
Running the following simple code (C++11)
#include <iostream>
using namespace std;
class test {
public:
int par;
test(int par_) : par(par_) {
cout << "constructor (par = " << par << " )" << endl;
}
test( int par_, char dummy) {
test( (int)par_ );
}
test() { test(100); }
// Copy constructor
test(const test& x) { cout << "copy constructor (par = " << x.par << " )" << endl; }
// Move constructor
test(test&& x) { cout << "move constructor (par = " << x.par << " )" << endl; }
// Copy assignemnt
test& operator=(const test& x) { cout << "copy assignemnt (par = " << x.par << " )" << endl; return *this; }
// Move assignement
test& operator=(test&& x) { cout << "move assignemnt (par = " << x.par << " )" << endl; return *this; }
~test() { cout << "destructor (par was " << par << " )" << endl; }
};
/****************************************************************************/
int main() {
cout << "=========================" << endl;
test tst_2(10, 0);
cout << "=========================" << endl;
test tst_1(5);
cout << "=========================" << endl;
test tst_0;
cout << "=========================" << endl;
cout << tst_2.par << " " << tst_1.par << " " << tst_0.par << endl;
return 0;
}
I get the output
=========================
constructor (par = 10 )
destructor (par was 10 )
=========================
constructor (par = 5 )
=========================
constructor (par = 100 )
destructor (par was 100 )
=========================
-858993460 5 -858993460
destructor (par was -858993460 )
destructor (par was 5 )
destructor (par was -858993460 )
Actually objects tst_2 and tst_0 are immediately destroyed ... and destroyed once again at the end of the execution!
However, if I replace the constructors section by the following
:
test(int par_) : par(par_) {
cout << "constructor 1 param (par = " << par << " )" << endl;
}
test( int par_, char dummy) : par(par_) {
cout << "constructor 2 params (par = " << par << " )" << endl;
}
test() : par(100) {
cout << "constructor 0 params (par = " << par << " )" << endl;
}
:
the behaviour is exactly what I'm expecting:
=========================
constructor 2 params (par = 10 )
=========================
constructor 1 param (par = 5 )
=========================
constructor 0 params (par = 100 )
=========================
10 5 100
destructor (par was 100 )
destructor (par was 5 )
destructor (par was 10 )
The question is: why does the first implementation destroy objects (which constructor calls another one) right after creation?
Upvotes: 0
Views: 59
Reputation: 449
You call test
from inside your constructor's body in two of the constructors. So, test
called inside your constructor is an object with a local scope. As soon as the program execution leaves one of those constructors, you local scope test
is destroyed, hence calling the destructor.
Upvotes: 0
Reputation: 25516
test( int par_, char dummy)
{
test( (int)par_ ); // secret is here!
}
At the marked line, you are creating another object on the stack, right within the contructor, which is destroyed again after the constructor is left. If you want to do constructor forwarding (as possible since C++11), you have to do it this way:
test( int par_, char dummy) : test(par_)
{ }
All the same in your default constructor (test(100);
).
Upvotes: 2