使用全局 std::array 引用作为模板参数时如何简化参数?
How to simply the parameters when using a global std::array reference as a template parameter?
这在第 17 C++中有效:
template <std::size_t N, const std::array<int, N> & ARRAY> class Foo {};
constexpr std::array<int, 3> A{1, 2, 3};
void bar()
{
Foo<3, A> foo_a;
}
那么有没有办法避免在Foo
的模板参数中写入N
呢?因为我们可以很容易地从ARRAY.size()
中知道它.我试过这个,失败了:
template <template <size_t N> const std::array<int, N> & ARRAY> Foo {}; // Error.
无需指定引用的确切类型。您可以使用占位符:
#include<array>
template <auto& ARRAY> class Foo {
static constexpr auto N = ARRAY.size();
};
constexpr std::array<int, 3> A{1, 2, 3};
void bar()
{
Foo<A> foo_a;
}
如果你想在模板参数不是对std::array<int, ...>
的引用时得到错误,你可以编写一个类型特征,告诉你该类型是否是std::array
的实例化,并检查value_type
:
#include<array>
#include<type_traits>
template<typename>
struct is_std_array : std::false_type {};
template<typename T, std::size_t N>
struct is_std_array<std::array<T, N>> : std::true_type {};
template<typename T>
inline constexpr auto is_std_array_v = is_std_array<T>::value;
// std::remove_cvref_t will be part of C++20
template<typename T>
using remove_cvref_t = std::remove_cv_t<std::remove_reference_t<T>>;
template<auto& ARRAY>
class Foo {
using ARRAY_type = remove_cvref_t<decltype(ARRAY)>;
static_assert(is_std_array_v<ARRAY_type>,
"Foo requires reference to std::array of int as template argument!");
static_assert(std::is_same_v<typename ARRAY_type::value_type, int>,
"Foo requires reference to std::array of int as template argument!");
constexpr static auto N = ARRAY.size();
};
constexpr std::array<int, 3> A{1, 2, 3};
constexpr std::array<long, 3> B{1, 2, 3};
constexpr int C = 5;
void bar()
{
Foo<A> foo_a;
// Foo<B> foo_b; // Will give static_assert error message
// Foo<C> foo_c; // Will give static_assert error message
}
在 C++20 中将有一些概念,这将允许您编写一个概念来测试我现在正在使用static_assert
s 测试的属性,您将能够使用该概念代替模板参数中的auto
。
通过部分专业化的可能解决方案
template <auto const &>
class Foo;
template <std::size_t N, std::array<int, N> const & ARRAY>
class Foo<ARRAY>
{ };
所以你可以写
constexpr std::array<int, 3> A{1, 2, 3};
int main ()
{
Foo<A> foo_a;
}
相关文章:
- 如何反转整数参数包
- 使用C++库在Android项目中修改gradle中的cmake参数,用于插入指令的测试
- 如何使用默认参数等选择模板专业化
- 将强制转换简化为取决于参数的类型
- 标准对此指向成员函数类型模板参数有何说明?是我的代码有误,还是 MSVS 16.6 有问题?
- 使用全局 std::array 引用作为模板参数时如何简化参数?
- 如何简化模板模板参数中的enable_if别名
- 简化可变参数模板:删除一些专用项
- 简化模板参数
- 类成员中的相同参数:简化
- 简化模板参数
- 如何使用许多模板参数简化表示法,并在C++的另一个模板类中使用它
- "return-by-reference"或"pass-by-reference"参数何时与constexpr兼容?
- 如何使用typedef来简化作为函数指针的模板函数参数
- 如何将可变模板参数的特征值简化为一个值
- 模板参数简化
- 使模板参数公开的简化方法
- 编译器是否会将给出常量参数的简单函数简化为唯一的指令?
- 将函数作为参数传递以简化线程创建
- 指向具有简化参数的函数的指针