Can I initialize an array using the std::initializer_list object instead of brace-enclosed initializer?
As known, we can do this: http://en.cppreference
Other answered correctly said this is not possible upfront. But with little helpers, you can get pretty close
template
std::array make_array_impl(
std::initializer_list t,
std::index_sequence)
{
return std::array{ *(t.begin() + Ns) ... };
}
template
std::array make_array(std::initializer_list t) {
if(N > t.size())
throw std::out_of_range("that's crazy!");
return make_array_impl(t, std::make_index_sequence());
}
If you are open to more work arounds, you can put this into a class to catch statically-known length violations for the cases where you pass a braced init list. But be warned that most people who read this code will head-desk
template
struct ArrayInitializer {
template struct id { using type = U; };
std::array t;
template>
ArrayInitializer(typename id::type z)
:ArrayInitializer(z, std::make_index_sequence())
{
if(N > z.size())
throw std::out_of_range("that's crazy!");
}
template
ArrayInitializer(U &&... u)
:t{ std::forward(u)... }
{ }
private:
template
ArrayInitializer(std::initializer_list& t,
std::index_sequence)
:t{ *(t.begin() + Ns) ... }
{ }
};
template
std::array f(ArrayInitializer ai) {
return std::move(ai.t);
}
int main() {
f({1, 2, 3, 4, 5}); // OK
f({1, 2, 3, 4, 5, 6}); // "too many initializers for array"
std::initializer_list il{1, 2, 3, 4, 5};
f(il); // ok
}
Note that both the non-static case at the top of the answer and the "head-desk" case do only check whether you provide too few initializing elements, and errors out then, for the initializer_list case. If you provide too many for the initializer_list case, the trailing elements are just ignored.