Reputation: 2076
I read somewhere (cannot find the source now) that
MyClass *p1 = new MyClass;
and
MyClass *p2 = new MyClass();
are essentially equivalent, provided that MyClass
provides a default constructor. The compiler understands what I want to do and adds the empty parentheses.
If this is the case, why I am not allowed to write
throw MyException;
but have to use
throw MyException();
? (Yep, a question mark at the beginning of a line.)
To add some more confusion, the C++ FAQ suggests that the second usecase (new MyClass()
) does not invoke a constructor, but calls function defined with operator()
instead.
Upvotes: 2
Views: 109
Reputation: 254431
The compiler understands what I want to do and adds the empty parentheses.
No it doesn't; the two expressions aren't quite equivalent. The difference is in how the objects are are initialised: the first uses default-initialisation, while the second uses value-initialisation. So they are equivalent for classes that define a default constructor; otherwise, the first will leave POD objects uninitialised, while the second will initialise them to zero.
why I am not allowed to write
throw MyException;
?
MyException()
is an expression that creates a value-initialised temporary object; you can throw that just like you can throw the value of any other suitable expression.
MyException
isn't an expression; it's just a type name. You can only throw the value of an expression, so throw MyException;
is not valid. There's no way to create a default-initialised temporary.
To add some more confusion, the C++ FAQ suggests that the second usecase (new MyClass()) does not invoke a constructor, but calls function defined with operator() instead.
No it doesn't. It says that a declaration like List x();
declares a function with a return type List
, not (as one might think) a value-initialised object of type List
. It has nothing to do with new-expressions or operator()
.
Upvotes: 4
Reputation: 16168
Because you are not throwing new
exception, but rather constructing it.
Consider following:
MyException exception = MyException(); // works
MyException exception = MyException; // doesn't work
new MyException; // works
new MyException();// works
Upvotes: 1
Reputation: 258568
The situation listed in the FAQ is different and doesn't apply here.
MyException
is just a type name in the first case, and creates a variable in the second. That's just the syntax. Same as
MyException ex = MyException;
wouldn't compile, but
MyException ex = MyException();
would. The FAQ example illustrates simply the equivalent of:
MyException ex();
which would indeed be a function declaration, whereas:
MyException ex;
would.
There's no way that
throw MyException();
or
MyException ex = MyException();
could be interpreted as a function declaration, so they work.
Upvotes: 0