统一和价值初始化
Uniform and Value-initialization
我尝试对构造函数使用值初始化的成员使用值初始化(我不知道我是否真的使用好术语...)
所以...当我定义:
struct A
{
int a_;
};
我可以使用:
A a{5};
assert(m.a_==5);
但是,如果我想使用成员大括号初始值设定项和初始化列表构造函数
struct B
{
int b_ {1};
};
这无法编译 (c++14: http://ideone.com/MQ1FMU):
B b{2};
这里是错误:
prog.cpp:19:7: error: no matching function for call to 'B::B(<brace-enclosed initializer list>)'
B b{2};
^
prog.cpp:19:7: note: candidates are:
prog.cpp:10:8: note: constexpr B::B()
struct B
^
prog.cpp:10:8: note: candidate expects 0 arguments, 1 provided
prog.cpp:10:8: note: constexpr B::B(const B&)
prog.cpp:10:8: note: no known conversion for argument 1 from 'int' to 'const B&'
prog.cpp:10:8: note: constexpr B::B(B&&)
prog.cpp:10:8: note: no known conversion for argument 1 from 'int' to 'B&&'
概念上有什么区别?
非常感谢!
根据 C++11 规则,B
不是聚合类型。 C++11 [dcl.init.aggr]/1:
An aggregate is an array or a class (Clause 9) with no user-provided constructors (12.1), no brace-or-equal-initializers for non-static data members (9.2), no private or protected non-static data members (Clause 11), no base classes (Clause 10), and no virtual functions (10.3).
B
只有一个默认构造函数,因此不能从 braced-initializer-list {2}
初始化。
C++14 允许对聚合中的非静态数据成员使用 brace-or-equal-initializers。 N4140 [dcl.init.aggr]/1:
An aggregate is an array or a class (Clause 9) with no user-provided constructors (12.1), no private or protected non-static data members (Clause 11), no base classes (Clause 10), and no virtual functions (10.3).
使用相当直接的语义:没有指定初始化器的字段从它们的 brace-or-equal-initializer 初始化,如果有的话,否则用 {}
[dcl.init.aggr]/7:
If there are fewer initializer-clauses in the list than there are members in the aggregate, then each member not explicitly initialized shall be initialized from its brace-or-equal-initializer or, if there is no brace-or-equal-initializer, from an empty initializer list (8.5.4).
您的程序因此是有效的 C++14 (DEMO)。本质上,C++11 中禁止 brace-or-equal-initializer 是 C++14 纠正的一个错误。
我尝试对构造函数使用值初始化的成员使用值初始化(我不知道我是否真的使用好术语...)
所以...当我定义:
struct A
{
int a_;
};
我可以使用:
A a{5};
assert(m.a_==5);
但是,如果我想使用成员大括号初始值设定项和初始化列表构造函数
struct B
{
int b_ {1};
};
这无法编译 (c++14: http://ideone.com/MQ1FMU):
B b{2};
这里是错误:
prog.cpp:19:7: error: no matching function for call to 'B::B(<brace-enclosed initializer list>)'
B b{2};
^
prog.cpp:19:7: note: candidates are:
prog.cpp:10:8: note: constexpr B::B()
struct B
^
prog.cpp:10:8: note: candidate expects 0 arguments, 1 provided
prog.cpp:10:8: note: constexpr B::B(const B&)
prog.cpp:10:8: note: no known conversion for argument 1 from 'int' to 'const B&'
prog.cpp:10:8: note: constexpr B::B(B&&)
prog.cpp:10:8: note: no known conversion for argument 1 from 'int' to 'B&&'
概念上有什么区别? 非常感谢!
根据 C++11 规则,B
不是聚合类型。 C++11 [dcl.init.aggr]/1:
An aggregate is an array or a class (Clause 9) with no user-provided constructors (12.1), no brace-or-equal-initializers for non-static data members (9.2), no private or protected non-static data members (Clause 11), no base classes (Clause 10), and no virtual functions (10.3).
B
只有一个默认构造函数,因此不能从 braced-initializer-list {2}
初始化。
C++14 允许对聚合中的非静态数据成员使用 brace-or-equal-initializers。 N4140 [dcl.init.aggr]/1:
An aggregate is an array or a class (Clause 9) with no user-provided constructors (12.1), no private or protected non-static data members (Clause 11), no base classes (Clause 10), and no virtual functions (10.3).
使用相当直接的语义:没有指定初始化器的字段从它们的 brace-or-equal-initializer 初始化,如果有的话,否则用 {}
[dcl.init.aggr]/7:
If there are fewer initializer-clauses in the list than there are members in the aggregate, then each member not explicitly initialized shall be initialized from its brace-or-equal-initializer or, if there is no brace-or-equal-initializer, from an empty initializer list (8.5.4).
您的程序因此是有效的 C++14 (DEMO)。本质上,C++11 中禁止 brace-or-equal-initializer 是 C++14 纠正的一个错误。