聚合初始化 - 向量和数组

时间:2014-04-21 04:28:53

标签: c++ c++11

我知道以下陈述有效

std::vector<int> a{1,2,4} --->A (Aggregate Initialization)

或以下声明

std::vector<int> a;
a = {1,2,4};                ---->B  Variable already initialized. - Then aggregate initialization is called

但是在数组的情况下

 int c[3]={1,4};  ---->C (1,4,0)

但是不允许以下内容

int c[3]; 
c = {1,4};   ---->D

现在我的问题是为什么B工作而D不工作?

2 个答案:

答案 0 :(得分:4)

正如其他答案中所解释的,此分配的机制是向量std::initializer_list assignment operator。尽管std::vector<int>不是聚合,但是使用大括号括起来的任意值初始化列表列表可以实现以下功能:

std::vector<int> a;
a = {1,2,4};       // OK, vector& operator=(std::initializer_list<T>)
  

但是不允许以下内容

int c[3]; 
c = {1,4}; // Error: arrays are not assignable

这是因为数组不可分配。如果它是一种不同类型的聚合,那么这将起作用。例如,

struct Foo { int a, b, c; }; // aggregate
Foo f = {1, 2, 3};           // OK, aggregate initialization
f = { 1, 4 };                // OK

此处,f.af.bf.c分别为1, 4, 0分配值。

此外,当非({ - 1}})构造函数具有与列表元素兼容的参数列表时,非聚合也可以使用大括号括起的初始化列表进行初始化和赋值。例如,

explicit

答案 1 :(得分:3)

std::vector<int> a{1,2,4};

这是初始化列表初始化,而不是聚合,因为vector不是聚合 - 它的数据存储在堆上。您需要#include <initializer_list>才能使用它,尽管该标头通常包含在<vector>中。

a = {1,2,4};

这也通过std::initializer_list上的函数重载,语义与函数调用相同:

a.assign( {1,2,4} );
 int c[3]={1,4};

聚合初始化。但是之后你不能做c = { 3, 5, 6 },因为braced-init-lists只能是新变量的初始值设定项,而不是内置表达式的操作数。 (在声明中,=符号只是初始化的符号。它不是通常的运算符。赋值运算符的语法特别允许使用支撑列表,但这种用法仅对函数重载有效,这会导致用于初始化新变量的列表:函数参数。)

最后一个问题的答案是,无法为“裸”数组编写必要的operator =重载,因为它必须是成员函数。解决方法是使用std::copystd::initializer_list对象。