Fido
Fido

Reputation: 330

How to emplace to a std::vector of std::array?

With a vector of vectors, I can do this:

std::vector<std::vector<int>> vov;
vov.emplace_back(std::initializer_list<int>{0, 0});

However, the equivalent fails for the vector of std::array:

std::vector<std::array<int, 2>> voa;
voa.emplace_back(std::initializer_list<int>{0,0});

What is the correct way to emplace an array inside vector?

Edit:

Yes, you can create std::array from initializer list:

std::array<int, 2> a = {0, 0}

works fine.

The error:

error C2664: 'std::array<int,2>::array(const std::array<int,2> &)': cannot convert argument 1 from 'std::initializer_list<int>' to 'const std::array<int,2> &'

Upvotes: 4

Views: 1557

Answers (1)

IlCapitano
IlCapitano

Reputation: 2094

std::array doesn't have any constructors, it's initialization follows aggregate initialization.

You have two options, either use push_back instead of emplace_back with a brace-init-list:

voa.push_back({ 0, 0 });

Or you can use std::array's (implicit) copy and move constructors and construct a temporary std::array:

voa.emplace_back(std::array<int>{0, 0}); // pre C++17
voa.emplace_back(std::array{0, 0});      // C++17

Ultimately both methods should generate the same machine code.


In response to your edit:

std::array<int, 2> a = {0, 0};

is NOT the same as

std::array<int, 2> a = std::initializer_list<int>{0, 0};

{0, 0} is a brace-init-list, which doesn't have a type. This is why you can't use them as an argument to a templated function. See this question for more details.

Upvotes: 13

Related Questions