用于合计
struct S{int i, j;};声明S s({1, 2});和S s({1});根据N3797§8.5 p16执行直接初始化:
窗体中发生的初始化。 (A);{a}; 在
new表达式(5.3.4)、static_cast表达式(5.2.9)、函数表示法类型转换(5.2.3)以及基和成员初始化器(12.6.2)中,都称为直接初始化。
但第8.5条p17似乎并没有描述它们的特点:
初始化器的语义如下。目标类型是正在初始化的对象或引用的类型,源类型是初始化器表达式的类型。如果初始化器不是单个(可能是括号大小)表达式,则不定义源类型。
char16_t数组、char32_t数组或wchar_t数组,而初始化器是字符串文本,请参见8.5.2。(),则对象为值初始化.- If the initialization is direct-initialization, or if it is copy-initialization where the cv-unqualified version of the source type is the same class as, or a derived class of, the class of the destination, constructors are considered. The applicable constructors are enumerated (13.3.1.3), and the best one is chosen through overload resolution (13.3). The constructor so selected is called to initialize the object, with the initializer expression or _expression-list_ as its argument(s). If no constructor applies, or the overload resolution is ambiguous, the initialization is ill-formed.
- Otherwise (i.e., for the remaining copy-initialization cases), user-defined conversion sequences that can convert from the source type to the destination type or (when a conversion function is used) to a derived class thereof are enumerated as described in 13.3.1.4, and the best one is chosen through overload resolution (13.3). If the conversion cannot be done or is ambiguous, the initialization is ill-formed. The function selected is called with the initializer expression as its argument; if the function is a constructor, the call initializes a temporary of the cv-unqualified version of the destination type. The temporary is a prvalue. The result of the call (which is the temporary for the constructor case) is then used to direct-initialize, according to the rules above, the object that is the destination of the copy-initialization. In certain cases, an implementation is permitted to eliminate the copying inherent in this direct-initialization by constructing the intermediate result directly into the object being initialized; see 12.2, 12.8.
T”的表达式可以独立于cv-限定符cv1和cv2初始化“cv2T”类型的对象。
int a;const int b= a;int c= b;
-尾注主题声明,S s({1, 2});和S s({1});
()。发布于 2014-01-10 12:26:11
本例在标准中涵盖了:它是第8.5/17节第6项(强调我的):
如果目标类型是(可能是cv限定的)类类型:
Explanation:我们首先注意到,S是一个集合(第8.5.1/1节)。但是聚合也是类,因此具有隐式声明的默认复制/移动构造函数(见第12.8节)。这两个构造函数都有一个论点,因此是可行的(由第13.3.2节)。他们的签名与往常一样:
S(const S&) //copy
S(S&&) //move现在,我们必须确定转换序列,以将初始化程序列表{1,2}转换为参数类型。§13.3.3.1.5/6指出:
否则,如果参数是引用,请参见13.3.3.1.4。注意:本节中的规则将适用于为引用初始化基础临时文件。-end注记
由于参数类型是引用的,因此适用第13.3.3.1.4/2号编:
当引用类型的参数没有直接绑定到参数表达式时,转换序列是根据13.3.3.1将参数表达式转换为引用的底层类型所必需的序列。概念上,此转换序列对应于使用参数表达式对基础类型的临时进行复制初始化。顶级cv限定中的任何差异都包含在初始化本身中,并不构成转换。
由于S是一个聚合,所以我们必须应用§13.3.3.1.5/5来初始化这个临时对象:
否则,如果参数具有可以根据聚合初始化规则(8.5.1)从初始化程序列表中初始化的聚合类型,则隐式转换序列是用户定义的转换序列,第二标准转换序列是标识转换。
因此,我们最终到达了这个临时对象的聚合初始化。要确定这两个构造函数中哪一个是最好的可行函数,必须查阅第13.3.3.2节(留给读者使用)。由于引用绑定到临时对象,因此将实际选择移动构造函数。
发布于 2014-01-10 01:55:58
声明
S s({1, 2});和S s({1});根据N3797§8.5 p16执行直接初始化。
好吧,是和不是。在第一种情况下,与第二种情况类似,S x-value对象是用{1, 2}构造的,然后传递给s l-值的隐式声明的复制构造函数。
这不是§8.5 p16正在讨论的情况,因为初始化不是以以下形式进行的:
S s(a);
S s{a};除非标准认为a是任何东西。即使如此,它也不是他在后面定义的其他案例的一部分(new、static_cast等)。
主题声明、
S s({1, 2});和S s({1});不是列表初始化,因为每个初始化器都是括号大小的大括号-init-列表。
表达式{1, 2}和{1}绝对是临时/到期S对象的列表初始化。
https://stackoverflow.com/questions/20973417
复制相似问题