ClassA a; vs. ClassA a();

What's the difference between
ClassA a;
ClassA a();

Open in new window

deleydAsked:
Who is Participating?

Improve company productivity with a Business Account.Sign Up

x
 
evilrixConnect With a Mentor Senior Software Engineer (Avast)Commented:
>> ClassA * aptr = new ClassA();
>> In the above case, the parens are superfluous. Either way, you get the default constructor.

Actually, that's also not true. In the case of POD or intrinsic types, not calling the synthesized constructor explicitly leaves the object uninitialised. Calling it explicitly constructs them with default values.

int * p = new int

is not the same as

int * p = new int()

The same is true for user defined PODs.

#include <iostream>

struct foo
{
   int bar;
};

int main()
{
   // aggregate members are not default initialised
   foo const * f1 = new foo;

   // aggregate members are default initialised
   foo const * f2 = new foo();

   std::cout
         << f1->bar << std::endl // output is indeterminate
         << f2->bar << std::endl; // output will be 0 (same as int()).

   delete f1;
   delete f2;
}

Open in new window


More specifically, the standard says...



To value-initialize an object of type T means:
— if T is a (possibly cv-quali¿ed) class type (Clause 9) with a user-provided constructor (12.1), then the
default constructor for T is called (and the initialization is ill-formed if T has no accessible default
constructor);
— if T is a (possibly cv-quali¿ed) non-union class type without a user-provided constructor, then the object
is zero-initialized and, if T’s implicitly-declared default constructor is non-trivial, that constructor is
called.
— if T is an array type, then each element is value-initialized;
— otherwise, the object is zero-initialized.

An object whose initializer is an empty set of parentheses, i.e., (), shall be value-initialized.

To default-initialize an object of type T means:
— if T is a (possibly cv-quali¿ed) class type (Clause 9), the default constructor for T is called (and the
initialization is ill-formed if T has no accessible default constructor);
— if T is an array type, each element is default-initialized;
— otherwise, no initialization is performed.

If no initializer is speci¿ed for an object, the object is default-initialized; if no initialization is performed, an
object with automatic or dynamic storage duration has indeterminate value.


And with regards to the "most vexing parse" rule, the standard states...


Note: Since () is not permitted by the syntax for initializer, X a(); is not the declaration of an object of class X, but the declaration of a function taking no argument and
returning an X.
0
 
jkrCommented:
In short: There is none. Both instantiate an instance of 'ClassA' via the default constructor. The 2nd line could be called more explicit, yet the brackets could as well be called superfluous.
0
 
evilrixSenior Software Engineer (Avast)Commented:
The first constructs an object called a.  The second declares a function called a.
0
Get your problem seen by more experts

Be seen. Boost your question’s priority for more expert views and faster solutions

 
evilrixSenior Software Engineer (Avast)Commented:
>>In short: There is none.
The standard disagrees.  Due to the "most vexing parse"  rule, the second is a function declaration.
0
 
evilrixSenior Software Engineer (Avast)Commented:
0
 
phoffricCommented:
ClassA * aptr = new ClassA();

In the above case, the parens are superfluous. Either way, you get the default constructor.
0
 
jkrCommented:
>> Due to the "most vexing parse"  rule, the second is a function declaration.

Even within a function's body? ;o)
0
 
phoffricConnect With a Mentor Commented:
Here is how to (1) remove the error from the "most vexing parse" problem in the link; and (2) how to force the TimeKeeper constructor to be called, rather than treating time_keeper as a function declaration.
class Timer {
 public:
	 Timer() { cout << "Timer" << endl;};
};
 
class TimeKeeper {
 public:
	 TimeKeeper(const Timer& t) {cout << "TimeKeeper" << endl;};
	 int get_time() {cout << "get_time" << endl; return 1;};
};
 
int main() {
  TimeKeeper time_keeper((Timer()));
  return time_keeper.get_time();
}

Open in new window

0
 
phoffricCommented:
oops - I just saw that the link mentioned this. So, never mind.
0
 
evilrixSenior Software Engineer (Avast)Commented:
>Even within a function's body? ;o)

Yes,  anywhere.

NB. You can forward declare a function within the scope of another function. This limits the scope to the function into which the other function is declared.
0
 
eeeabhiCommented:
ClassA a;//Create an instance of Object type ClassA with the instance name a
ClassA a();//Declare a function which returns ClassA type object and takes in no arguments.
0
 
evilrixSenior Software Engineer (Avast)Commented:
eeeabhi, we have already established that.
0
 
deleydAuthor Commented:
Most vexing. This C++ syntax will drive me nuts.
0
Question has a verified solution.

Are you are experiencing a similar issue? Get a personalized answer when you ask a related question.

Have a better answer? Share it in a comment.

All Courses

From novice to tech pro — start learning today.