模板推导指南可以调用 constexpr 函数吗?
Can template deduction guides call constexpr functions?
我有自己的固定大小的数组类型,我想 constexpr
可以从 std::initializer_list
构造,而不必显式定义大小模板参数。
我以为我可以使用模板推导指南,但看起来它没有将 std::initializer_list::size()
视为它的 constexpr 函数。
下面是尝试为std::array
做一个推导指南的例子(和我的类型相似,也有同样的问题):
namespace std
{
template<typename T> array(initializer_list<T> initialiserList) -> array<T, initialiserList.size()>;
}
static constexpr std::array myArray = {1,2,3};
static constexpr std::array myArray2 = {{1,2,3}};
我试过 MSVC 和 Clang,两者都给出大致相同的错误:
myArray
出错,抱怨函数的参数太多。
myArray2
说 "substitution failure [with T = int]: non-type template argument is not a constant expression"
我尝试将 constexpr
放在推导指南或函数参数的前面,但似乎都不允许,因此推导指南似乎无效,即使它在 [=11] 中应该可以正常工作=]上下文。
有没有办法在不走 make_array()
路线的情况下完成这项工作?
Parameter/argument 值不是 constexpr
.
您可以使用可变参数模板在编译时知道大小,或者键入已知大小(std::array
或 C 数组引用)。
Is there a way to make this work without going down the make_array()
route?
你为什么不试试下面的推导指南?
template <typename T, std::size_t N>
array(T const (&)[N]) -> array<T, N>;
这样,myArray2 = {{1,2,3}}
中的参数不会被解释为 std::initializer_list
(因为参数不能被视为 constexpr
,所以它是 size()
't 用于模板参数)但作为 C 样式数组。
因此可以推断,作为模板参数,类型和大小(T
和N
)以及大小(N
)都可以用作模板参数。
你可以这样做:
template <class T, class... U>
array(T, U...) -> array<T, 1 + sizeof...(U)>;
问题不在于你不能调用演绎指南中的constexpr
函数。你可以。这个例子很荒谬,但有效:
constexpr size_t plus_one(size_t i) { return i + 1; }
template <class T, class... U>
array(T, U...) -> array<T, plus_one(sizeof...(U))>;
问题在于函数参数不是 constexpr
对象,因此如果这些成员函数读取某种本地状态,则您不能对其调用 constexpr
成员函数。
我有自己的固定大小的数组类型,我想 constexpr
可以从 std::initializer_list
构造,而不必显式定义大小模板参数。
我以为我可以使用模板推导指南,但看起来它没有将 std::initializer_list::size()
视为它的 constexpr 函数。
下面是尝试为std::array
做一个推导指南的例子(和我的类型相似,也有同样的问题):
namespace std
{
template<typename T> array(initializer_list<T> initialiserList) -> array<T, initialiserList.size()>;
}
static constexpr std::array myArray = {1,2,3};
static constexpr std::array myArray2 = {{1,2,3}};
我试过 MSVC 和 Clang,两者都给出大致相同的错误:
myArray
出错,抱怨函数的参数太多。
myArray2
说 "substitution failure [with T = int]: non-type template argument is not a constant expression"
我尝试将 constexpr
放在推导指南或函数参数的前面,但似乎都不允许,因此推导指南似乎无效,即使它在 [=11] 中应该可以正常工作=]上下文。
有没有办法在不走 make_array()
路线的情况下完成这项工作?
Parameter/argument 值不是 constexpr
.
您可以使用可变参数模板在编译时知道大小,或者键入已知大小(std::array
或 C 数组引用)。
Is there a way to make this work without going down the
make_array()
route?
你为什么不试试下面的推导指南?
template <typename T, std::size_t N>
array(T const (&)[N]) -> array<T, N>;
这样,myArray2 = {{1,2,3}}
中的参数不会被解释为 std::initializer_list
(因为参数不能被视为 constexpr
,所以它是 size()
't 用于模板参数)但作为 C 样式数组。
因此可以推断,作为模板参数,类型和大小(T
和N
)以及大小(N
)都可以用作模板参数。
你可以这样做:
template <class T, class... U>
array(T, U...) -> array<T, 1 + sizeof...(U)>;
问题不在于你不能调用演绎指南中的constexpr
函数。你可以。这个例子很荒谬,但有效:
constexpr size_t plus_one(size_t i) { return i + 1; }
template <class T, class... U>
array(T, U...) -> array<T, plus_one(sizeof...(U))>;
问题在于函数参数不是 constexpr
对象,因此如果这些成员函数读取某种本地状态,则您不能对其调用 constexpr
成员函数。