Reputation: 2675
The following is the smallest program that replicates my problem:
#include <iostream>
using namespace std;
class Test
{
public:
Test()
{
_a = 0;
}
Test(int t)
{
Test();
_b = t;
}
void Display()
{
cout << _a << ' ' << _b << endl;
}
private:
int _a;
int _b;
};
int main()
{
Test test(10);
test.Display(); // 70 10
return 0;
}
When I do this, _a
is initialized with garbage. Why does this happen? Is there a problem when a constructor is invoked from within another?
Upvotes: 3
Views: 76
Reputation: 372814
The issue here is in this code:
Test(int t)
{
Test();
_b = t;
}
This does not call the default Test
constructor, then set _b = t
. Instead, it creates a temporary object of type Test
using the default constructor, ignores that temporary object, then sets _b = t
. Consequently, the default constructor won't run for the receiver object, so _a
will remain uninitialized.
To fix this, in C++11, you can write
Test(int t) : Test() {
_b = t;
}
which does call the default constructor, or (in C++03) you can factor out the initialization code from the default constructor into a helper member function that you call from both the default and parameterized constructor:
Test() {
defaultInit();
}
Test(int t) {
defaultInit();
_b = t;
}
Or, if you have a C++11 compiler, just eliminate the default constructor by using default initializers, like this:
class Test
{
public:
Test() = default;
Test(int t)
{
_b = t;
}
void Display()
{
cout << _a << ' '<< _b << endl;
}
private:
int _a = 0;
int _b;
};
Hope this helps!
Upvotes: 10