Use of new T; instead of new T();

There is a recurring pattern in the code base that I thought I would bring some awareness to.

Programmers use…

auto obj = new Class();

While this works, it is explicitly calling the constructor () for the class, even if it doesn’t have one. This forces the compiler to generate a constructor for that signature for you. When the code runs, this call to a constructor takes time.

I made a small test app to demonstrate this. Here are the results.

Default is new Class; and Explicit is new Class()

Simulator/Default  100000000 new in 3.788020 seconds
Simulator/Explicit 100000000 new in 4.679787 seconds    21.0625% difference

Device/Default  10000000 new in 1.718966 seconds
Device/Explicit 10000000 new in 1.830327 seconds     6.2751% difference

If you leave off the () then the compiler doesn’t do anything, which executes quite a bit faster. This only affects the case where there is no constructor, but for some structs and classes that you need to be blazingly fast, this could be important.

auto obj = new Class;

This is all you need, and should be the preferred way to instantiate an object.

2 Likes

i t would be interesting to compare the situation where there is an existing, empty constructor - which I create for all my classes out of habit!

This sounds like a micro optimization, I would hardly recommend this as a preferred way to instantiate object as it leaves member variables uninitialized (instead of value-initialized) which is a source of bugs. And eventually you will need to put some real values to your struct anyway for it to be of any use, so i’m not sure about the performance gain here (as opposed to passing the initial values in the constructor for example). You might get less icache misses as the constructor is missing, but should hardly be a huge performance gain.

This more about being aware of how it works. Most programmers don’t know the difference between explicitly calling the default destructor and the compiler generated one.

This only applies to classes/structs that don’t have a parameterless constructor. Objects with a constructor that initializes member variables will still be called even when you leave off the (), so there is no source of bugs there.

Where this becomes important is in situations where you don’t want to initialize member variables because you are about to set them. For example, when loading a save game, or loading a 3d model, where you are likely to have large arrays of POD objects.

I recommend it because it allows the compiler to choose. Calling the default constructor explicitly forces the compiler to generate for you if you haven’t provided one.

Justin