给定参数签名std::array<const size_t, V> shape
的函数,如:
template<int V>
struct Cls {int val(){return V;} };
template <int V>
auto make(std::array<const size_t, V> shape) -> Cls<V>{
return Cls<V>();
}
我需要始终添加模板参数V
,如
auto t1 = make<2>({2, 3}); // does work but need the information twice
std::cout << t1.val() << std::endl;
因为braced-initializer列表似乎被转换为c ++ 11 std::array
。但是,这在我看来是多余的。 {2, 3}
的长度为2。我知道它,编译器也应该知道它。是否可以将其包装成:
// auto t0 = make({2, 3}); // doesn't work
// auto t0 = make(2, 3); // would be also ok
我尝试过将std::array
的大小确定为constexpr
。但我无法摆脱模板参数<2>
。
template <int V>
constexpr size_t arr_len(std::array<const size_t, V>){return V;}
template <typename V>
auto make2(V shape) -> Cls<arr_len(shape)>{
return Cls<arr_len(shape)>();
}
我在这里添加了一个可运行的MWE:
此thread似乎有关,但我不知道它可能会有什么帮助。 有什么建议吗?
答案 0 :(得分:2)
我想您可以使用可变make()
函数(在以下示例中为make0()
),可以将大小计算为sizeof...(Is)
以下是一个完整的工作示例
#include <array>
#include <iostream>
template<int V>
struct Cls {int val(){return V;} };
template <int V>
auto make(std::array<const size_t, V> shape) -> Cls<V>{
return Cls<V>();
}
template <typename ... Is>
auto make0 (Is ... is) -> Cls<sizeof...(Is)>
{ return make<sizeof...(Is)>({ {std::size_t(is)... } }); }
int main ()
{
auto t1 = make0(2, 3, 5, 7);
std::cout << t1.val() << std::endl;
}