0

I have the following code:

#include<iostream>
using namespace std;

class A{
private:
    int x;
public:
    A(){x=10;}
    
    A(int m){x=m; cout << "int m constructor" << m << endl;}
    A(A& a){cout << "copy constructor:"<<a.x<<"\n"; x=a.x;}
    A(A&& a){cout <<"move constructor:"<<a.x<<"\n"; x=a.x;}

};

int main(){
    A a(100);
    A b = a;

    A d = A(30);
    
}

which outputs the following:

int m constructor100
copy constructor:100
int m constructor30

I was expecting it to output

int m constructor100
copy constructor:100
copy constructor:30

because the constructor function (A(30)) is called. But somehow the compiler optimises it? Also A d = A(A(30)) also prints int m constructor30. Is there some compiler optimization happening here?

A J
  • 1
  • Your last line (`A d = A(30)`) is actually a direct initialization of `d` (no need to create a temporary and then copy construct/assign). – wohlstad Jul 18 '22 at 14:38
  • *When exactly is copy constructor called?* -- Whenever the compiler makes a copy. There is no *exact* answer as to the number of times, and that is especially the case if you compile your program using different options. That's why when writing user-defined copy constructors, it should be coded to have no side-effects, no complex "business logic", etc. because you won't reliably predict exactly when it will be called. – PaulMcKenzie Jul 18 '22 at 14:40
  • `A d = A(30)` is evaluated as if it were `A d(30)`, because C++ presumes that there is no benefit in default-constructing an object only to immediately assign something else to it. – Drew Dormann Jul 18 '22 at 14:41
  • https://en.cppreference.com/w/cpp/language/copy_elision ; but also you should implement assignment ops, to see the whole picture in different scenarios. – pptaszni Jul 18 '22 at 14:41
  • Side-effects in constructors are not guaranteed to be executed, because constructors *can be* (and as of C++17 and later, *must be*) elided where they are redundant. It's not a "compiler optimization" inasmuch as it is a requirement by the language. – Eljay Jul 18 '22 at 14:55

1 Answers1

0

Your last line A d = A(30) and A d = A(A(30)) is the mandatory copy elision.

Goswin von Brederlow
  • 11,875
  • 2
  • 24
  • 42