I know the following statements work
std::vector<int> a{1,2,4} --->A (Aggregate Initialization)
or the following statement(s)
std::vector<int> a;
a = {1,2,4}; ---->B Variable already initialized. - Then aggregate initialization is called
However in case of Arrays
int c[3]={1,4}; ---->C (1,4,0)
However the following is not allowed
int c[3];
c = {1,4}; ---->D
Now my question is why does B work and D doesnt ?
std::vector<int> a{1,2,4};
This is initializer-list initialization, not aggregate, because vector
is not an aggregate — its data is stored on the heap. You need to have #include <initializer_list>
for it to work, although that header is typically included from <vector>
.
a = {1,2,4};
This also goes through a function overloaded on std::initializer_list
, and the semantics are the same as the function call:
a.assign( {1,2,4} );
int c[3]={1,4};
This is aggregate initialization. However you cannot do c = { 3, 5, 6 }
afterward, because the braced-init-lists may only be initializers for new variables, not operands to built-in expressions. (In a declaration, the =
sign is just a notation for initialization. It is not the usual operator. Braced lists are specifically allowed by the grammar for assignment operators, but this usage is only valid with function overloading, which causes the list to initialize a new variable: the function parameter.)
The answer to your final question is that there's no way to write the necessary operator =
overload for "naked" arrays, because it must be a member function. The workaround is to use std::copy
and a std::initializer_list
object.
As has been explained in other answers, the mechanism for this assignment is the vector's std::initializer_list
assignment operator . This makes the following possible with brace enclosed initializer lists of arbitrary value, despite std::vector<int>
not being an aggregate:
std::vector<int> a;
a = {1,2,4}; // OK, vector& operator=(std::initializer_list<T>)
However the following is not allowed
int c[3];
c = {1,4}; // Error: arrays are not assignable
This is because arrays are not assignable. If it were a different kind of aggregate, then this would work. For example,
struct Foo { int a, b, c; }; // aggregate
Foo f = {1, 2, 3}; // OK, aggregate initialization
f = { 1, 4 }; // OK
Here, fa
, fb
and fc
are assigned the values 1, 4, 0
respectively.
Furthermore, non-aggregates can also be initialized and assigned-to with brace-enclosed initializer lists when they have (non- explicit
) constructors with a parameter list compatible with the elements of the list. For example,
struct Bar
{
Bar(int a, int b, int c) : a(a), b(b), c(c) {} // non-aggregate
int a, b, c;
};
Bar b0 = {1, 2, 3}; // OK
Bar b1 = {1,2}; // Error: number of elements must be 3
b0 = {11, 22, 33}. // Assignemnt OK
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.