Home > Back-end >  Must consteval constructor initialize all data members?
Must consteval constructor initialize all data members?

Time:02-12

In the next program struct B has immediate consteval default constructor, which does not initialize i field. Then this constructor is used to make a temporary and its i field remains untouched:

struct B {
    bool b = true;
    int i;
    consteval B() {}
};

static_assert( B{}.b );

Clang and MSVC are fine with it. But GCC complains:

 error: 'B{true}' is not a constant expression
    7 | static_assert( B{}.b );
      |                  ^
error: 'B()' is not a constant expression because it refers to an incompletely initialized variable

Demo: https://gcc.godbolt.org/z/x4n6ezrhT

Which compiler is right here?

CodePudding user response:

From cppreference's consteval specifier (since C 20):

The consteval specifier declares a function or function template to be an immediate function,
...
An immediate function is a constexpr function, and must satisfy the requirements applicable to constexpr functions or constexpr constructors, as the case may be.

And if we go to cppreference's constexpr specifier (since C 11):

A constexpr function must satisfy the following requirements:
...
A constexpr constructor whose function body is not =delete; must satisfy the following additional requirements:
...
for the constructor of a class or struct, every base class sub-object and every non-variant non-static data member must be initialized.

However, as @user17732522 accurately pointed out in a comment below, this last requirement applies only until C 20.

So I would say i doesn't need to be initialized in this case (Clang/MSVC are correct, gcc is wrong).

  • Related