Thursday, April 7, 2022

[SOLVED] gcc: invalid error "use of deleted function" (copy constructor)?

Issue

Simplified issue:

#include <stdio.h>
class X
{
public:
    int a = 0;
    X() { printf("constr-def %d\n", a); }
    X(int i):a(i+1) { printf("constr-i %d\n", a); }
    int operator=(int i) { a = i; return i; }
    operator bool() { return !!a; }
    
    //~ X(const X& o) { a = o.a; printf("copy-constr %d\n", a); };
    //~ const X& operator=(const X& o) { a = o.a; printf("copy-op %d\n", a); return *this; };
    
    X(const X& o) = delete;
    const X& operator=(const X& o) = delete;
};

int main() {
    X x;
    X y = 5;  // should be equivalent to X y(5)
    printf("results: %d %d\n", x.a, y.a);
}

Output when compiled as is with MSVC; or with gcc / MSVC and non-deleted copy constructor variants active (commented out above):

>g++ -Os dede.cpp -o dede
>dede
constr-def 0
constr-i 6
results: 0 6
>Exit code: 0

--> Copy constructor is never used; MSVC compiles successfully as is.

Compile as is with gcc (v9.3.0 current mingw/msys64 build):

>g++ -Os dede.cpp -o dede
dede.cpp: In function 'int main()':
dede.cpp:20:8: error: use of deleted function 'X::X(const X&)'
   20 |  X y = 5;  // should be equivalent to X y(5)
      |        ^
dede.cpp:14:5: note: declared here
   14 |     X(const X& o) = delete;
      |     ^
dede.cpp:7:2: note:   after user-defined conversion: 'X::X(int)'
    7 |  X(int i):a(i+1) { printf("constr-i %d\n", a); }
      |  ^
>Exit code: 1

Why does gcc error out with use of deleted copy constructor, when he doesn't use it in the non-deleted case?


Solution

Before C++17 such copy elision is an optimization, which is permitted but the copy (or move) constructor still must be present and accessible.

Since C++17 the code works fine because for mandatory copy elision the copy/move constructors need not be present or accessible again.

C++17 core language specification of prvalues and temporaries is fundamentally different from that of the earlier C++ revisions: there is no longer a temporary to copy/move from.



Answered By - songyuanyao
Answer Checked By - Marie Seifert (WPSolving Admin)