C++ 允许实例化一个类,通过初始化列表设置公共(public)成员的值,如下例所示 b1
:
class B {
public:
int i;
std::string str;
};
B b1{ 42,"foo" };
B b2();
;但是,如果我提供构造函数
B(int k) { }
,它不会编译。
那么,幕后发生了什么?
是不是当没有提供构造函数时,编译器会提供一个?但是它怎么能提供一个初始化列表呢?我认为它只会提供一个不接受任何输入的“空白”构造函数,如 b2
的示例所示。还是两者都提供?
最佳答案
But how could it provide one with initialization list?
不,不会。
注意对于 list initialization B b1{ 42,"foo"};
, aggregate initialization执行。
If
T
is an aggregate type, aggregate initialization is performed.
B
是一个aggregate type ,
An aggregate is one of the following types:
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 b1{42};
或 B b2(42);
一样初始化 B
,这将调用适当的构造函数。
顺便说一句:在提供了一个用户定义的构造函数(带一个参数)之后,implicitly-declared default constructor不会被编译器再次声明。这意味着 B b2;
或 B b2{};
将不再有效。
BTW2:B b2();
可能是一个函数声明。参见 Most vexing parse .
关于C++:如何通过初始化列表进行构造?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39442895/