3

C++允许实例化一个类,经由初始化列表设置公共成员的值,如下面示出了例如用于b1C++:如何通过初始化列表完成构造?

class B { 
public: 
    int i; 
    std::string str; 
}; 

B b1{ 42,"foo" }; 
B b2(); 

;然而,如果我提供的构造函数

B(int k) { } 

,它不会编译。

那么,引擎盖后面发生了什么? 当没有构造函数提供时,编译器会提供一个吗?但是它怎么能提供一个初始化列表?我认为它只会提供一个没有输入的“空白”构造函数,如b2所示。还是它提供了两个?

回答

5

但是它怎么能提供一个初始化列表?

不,它不会。

请注意,对于list initializationB b1{ 42,"foo" };,aggregate initialization执行。

如果T是聚合类型,则执行聚合初始化。

而且B一个aggregate type

聚集是以下类型之一:

array type 
class type (typically, struct or union), that has 

    no private or protected non-static data members 
    no user-provided, inherited, or explicit constructors (explicitly defaulted or deleted constructors are allowed) 
    no virtual, private, or protected base classes 
    no virtual member functions 

这就是为什么B b1{ 42,"foo" };效果很好。

而如果您提供用户定义的构造函数,B变为非聚合类型,那么聚合初始化将不会再工作。在这种情况下,您只能初始化B,如B b1{42};B b2(42);,它将调用相应的构造函数。

顺便说一句:在提供用户定义的构造函数(带一个参数)后,编译器不会再次声明implicitly-declared default constructor。这意味着B b2;B b2{};将不会再工作。

BTW2:B b2();可能是一个函数声明。见Most vexing parse

相关问题