Reputation: 4655
I'm playing around with C++20 NTTPs (non-type template parameters), and I was wondering, is there a way to convert between the elements of an NTTP std::array
and types in the form of T<int>
?
Consider this example:
template<int X>
struct Func;
template<auto ints>
struct Foo{
// This doesn't work because within the std::apply the ints isn't a constant expression.
constexpr auto funcs() const {
return std::apply([](auto... xs){ return std::tuple{Func<xs>{}...};}, ints);
}
};
constexpr Foo<std::array{1,2,3}> f;
constexpr auto funcs = f.funcs();
It easily works if the elements are values in a variadic NTTP pack, but having them in a std::array
would allow to use the full power of the standard library algorithms rather than having to operate on parameter packs through TMP (template metaprogramming).
template<int... ints>
struct Foo2{
// This here works, of course.
constexpr auto funcs() const {
return std::tuple{Func<ints>{}...};
}
};
constexpr Foo2<1,2,3> f2;
constexpr auto funcs = f2.funcs();
Full code here.
Upvotes: 2
Views: 244
Reputation: 76829
You can get a parameter pack with indices to the ints
array as template parameter pack using the std::index_sequence
method:
return []<std::size_t... I>(std::index_sequence<I...>){
return std::tuple{Func<ints[I]>{}...};
}(std::make_index_sequence<std::size(ints)>{});
Then ints[I]
can be used exactly as you intend xs
to be used in your example.
Upvotes: 2