Reputation: 101
I am working on a program that behaves differently when I set the default constructor to when I omit it. Specifically I am building an object to pass it to a third-party library function. When I omit the default constructor, the function works as expected, however when I define it the function blocks and does not return control, so I think the problem is due to the constructor.
Below I show a summary excerpt of the part of the code that has to do with the problem.
class Config {
public:
typedef std::shared_ptr<Config> SPtr;
int frame;
int numSolidParticles = 0;
bool shapesChanged = false;
Buffer* buffer;
FlexParams params; // struct
// if omitted then the 3rd party method works as expected
Config() {
}
};
...
Config::SPtr config = std::make_shared<Config>();
initialize(config);
...
SetFlexParams(config->params);
// calls to other 3rd party methods that depends on config
...
// call 3rd party library's method that causes the issue
mapBuffer(config->buffer);
Update: What I'm trying to do is moving some of the initializations (e.g. frame
, buffer
and other fields not shown) in method inititalize
to constructor.
Upvotes: 2
Views: 554
Reputation: 5856
Default default constructor does one thing your manual default constructor does not: it properly default-constructs the members. I'm pretty sure that if you do either of the following your code will magically start working:
Option 1: Explicitly state default values for all the members (not just the two you have done so for)
int frame = 0;
int numSolidParticles = 0;
bool shapesChanged = false;
Buffer* buffer = nullptr;
FlexParams params = {}; // struct
Option 2: Remember to initialize all non-trivially-constructible members in your constructor
Config()
: frame{0}
, numSolidParticles{0}
, shapesChanged{false}
, buffer{nullptr}
, params{} // I think this is the code generated by your compiler for the default default constructor
{
}
I personally prefer the first approach as it is clearer and way less prone to errors in a long run
Upvotes: 0
Reputation: 101
Although this does not answer the main question I would like to explain that the problem was being caused by a field of the FlexParams
struct that I was forgetting to initialize.
This struct groups a large number of parameters to 3rd party library that are initialized in the initialize
function. The funny thing is that when I do not define the constructor the field is initialized to 0 (which luckily was the correct value) while when I define it the field takes a random value.
The only reasonable explanation, as some of you mentioned in the comments, is that the issue was caused by undefined behavior.
Upvotes: 0
Reputation: 20579
What is the difference between a custom default constructor and defaulted default constructor?
Given a class X
, if: ([class.ctor]/5)
X
is a union that has a variant member with a non-trivial default constructor and no variant member ofX
has a default member initializer,
X
is a non-union class that has a variant member M with a non-trivial default constructor and no variant member of the anonymous union containing M has a default member initializer,any non-static data member with no default member initializer is of reference type,
any non-variant non-static data member of const-qualified type (or array thereof) with no brace-or-equal-initializer does not have a user-provided default constructor,
X
is a union and all of its variant members are of const-qualified type (or array thereof),
X
is a non-union class and all members of any anonymous union member are of const-qualified type (or array thereof),any potentially constructed subobject, except for a non-static data member with a brace-or-equal-initializer, has class type
M
(or array thereof) and eitherM
has no default constructor or overload resolution as applied to findM
's corresponding constructor results in an ambiguity or in a function that is deleted or inaccessible from the defaulted default constructor, orany potentially constructed subobject has a type with a destructor that is deleted or inaccessible from the defaulted default constructor.
then the defaulted default constructor of X
is defined as deleted, whereas a hand-written X() {}
will be ill-formed.
Otherwise, there is no difference.
Upvotes: 1