我试图理解@bolov 对问题 Deleted default constructor. Objects can still be created... sometimes 的第一个接受的答案[1]
我好像在那里发现了一个错误,所以它搞砸了整个解释。
@bolov 解释了为什么这段代码在 c++11 中成功编译:
场景A
struct foo {
foo() = delete;
};
// All bellow OK (no errors, no warnings)
foo f = foo{};
foo f = {};
foo f{}; // will use only this from now on.
为什么这段代码无法在 C++11 中编译:
场景 C
struct foo {
foo() = delete;
foo(int) {};
};
foo f{}; // error call to deleted constructor
他说重点是第一个foo是聚合,第二个foo不是聚合。
然后他给出了 cppreference 的摘录:
The effects of list initialization of an object of type T are: ...
- If T is an aggregate type, aggregate initialization is performed. This takes care of scenarios A B D E (and F in C++14)
Otherwise the constructors of T are considered in two phases:
All constructors that take std::initializer_list ...
otherwise [...] all constructors of T participate in overload resolution [...] This takes care of C (and F in C++11) ...
根据您在场景 A 中编写 foo f { }; 时的摘录,您将获得聚合初始化。那就太好了。但实际上在 c++11(#3337 草案,最接近标准)中你有不同的初始化顺序:
List-initialization of an object or reference of type T is defined as follows:
- If the initializer list has no elements and T is a class type with a default constructor, the object is value-initialized.
- Otherwise, if T is an aggregate, aggregate initialization is performed (8.5.1)
所以 foo f { }; 在场景 A 中应该会导致值初始化,也就是说,将调用 DELETED 默认构造函数并且代码应该失败编译。
最佳答案
由于 Core Issue 1301 ,这是针对 C++11 的缺陷,列表初始化的优先级从:
List-initialization of an object or reference of type T is defined as follows:
- If the initializer list has no elements and T is a class type with a default constructor, the object is value-initialized.
- Otherwise, if T is an aggregate, aggregate initialization is performed (8.5.1)
到:
List-initialization of an object or reference of type T is defined as follows:
- If T is an aggregate, aggregate initialization is performed (8.5.1)
- Otherwise, if the initialize list has no elements and T is a class type with a default constructor, the object is value-initialized.
所以场景 A 中的 foo{}
仍然是聚合初始化。
关于c++11 聚合初始化之前的值初始化,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39588505/