Designated Initializers in C 20: Initialization of Derived Classes
Designated initializers, introduced in C 20, allow for precise initialization of class members using a designated-initializer-list. However, a recent question sheds light on an unexpected behavior with derived classes.
Question:
The following code illustrates the issue:
<code class="cpp">struct Person { std::string name{}; std::string surname{}; unsigned age{}; }; struct Employee : Person { unsigned salary{10000}; }; int main() { Person p{.name{"John"}, .surname{"Wick"}, .age{40}}; // Ok Employee e1{.name{"John"}, .surname{"Wick"}, .age{40}, .salary{50000}}; // Doesn't compile Employee e2{.salary{55000}}; // Warning: missing initializer for base class }</code>
Why does the initialization of Employee with designated initializers fail and produce a warning for the missing initializer?
Answer:
According to the C 20 Standard (9.3.1 Aggregates, p. #3), when using designated initializers, each identifier in the designator must name a direct non-static data member of the class. This implies that base class members cannot be initialized using designated initializers.
Therefore, initializing Employee using designated initializers, as in the case of e1, is incorrect and should be replaced with either a list initialization or a nested initialization as follows:
<code class="cpp">Employee e1{"John", "Wick", 40, 50000}; // List initialization Employee e2{{"John", "Wick", 40}, 50000}; // Nested initialization Employee e1{{.name{"John"}, .surname{"Wick"}, .age{40}}, 50000}; // Nested initialization with designated initializer for base class</code>
In the last example, the base class Person is initialized using a designated initializer list within the nested initialization.
The above is the detailed content of Why Can\'t I Initialize Derived Class Members Using Designated Initializers in C 20?. For more information, please follow other related articles on the PHP Chinese website!