C++ 使用静态constexpr成员变量作为模板方法参数

C++ 使用静态constexpr成员变量作为模板方法参数,c++,templates,sfinae,C++,Templates,Sfinae,我试图通过将一些关于类的信息定义为静态constexpr成员来简化一些模板代码。下面是一个非常简单的示例: 样板 课堂测试 { 公众: 静态constexpr bool is_array=std::is_array\u v; 模板*dummy=nullptr> 空印 { 标准::cout 空印 { std::cout如果您希望SFINAE为类的方法工作,那么在您的例子中,您必须基于该方法的特定模板参数so U进行测试 如果检查is_array,则If依赖于类的模板参数,而不是依赖于U 但是,如果

我试图通过将一些关于类的信息定义为静态constexpr成员来简化一些模板代码。下面是一个非常简单的示例:

样板 课堂测试 { 公众: 静态constexpr bool is_array=std::is_array\u v; 模板*dummy=nullptr> 空印 { 标准::cout 空印 {
std::cout如果您希望SFINAE为类的方法工作,那么在您的例子中,您必须基于该方法的特定模板参数so U进行测试

如果检查is_array,则If依赖于类的模板参数,而不是依赖于U

但是,如果您至少可以使用C++14,就可以使用模板变量,这样就可以将is_数组模板化

另一种可能更好的方法是使用bool模板参数而不是U;例如

template <typename T>
struct Test
 {
   static constexpr bool is_array = std::is_array_v<T>;

   template <bool B = is_array,
             std::enable_if_t<not B>* = nullptr>
   void print()
    { std::cout << "It's not an array\n"; }

   template <bool B = is_array,
             std::enable_if_t<B>* = nullptr>
   void print()
    { std::cout << "It's an array\n"; }
 };

如果您想让SFINAE为类的方法工作,就必须对该方法的特定模板参数sou进行测试

如果检查is_array,则If依赖于类的模板参数,而不是依赖于U

但是,如果您至少可以使用C++14,就可以使用模板变量,这样就可以将is_数组模板化

另一种可能更好的方法是使用bool模板参数而不是U;例如

template <typename T>
struct Test
 {
   static constexpr bool is_array = std::is_array_v<T>;

   template <bool B = is_array,
             std::enable_if_t<not B>* = nullptr>
   void print()
    { std::cout << "It's not an array\n"; }

   template <bool B = is_array,
             std::enable_if_t<B>* = nullptr>
   void print()
    { std::cout << "It's an array\n"; }
 };

使用if constexpr分支打印一次怎么样?@bipll是的,在这种情况下会起作用。我必须使用if constexpr将一堆SFINAE选择的方法组合成大的方法。不过,它确实可以编译和工作。我正在寻找一种方法,让编译器选择正确的方法。我最终重构了代码,以便更好地使用ifconstexpr,这似乎是我想要的最干净的方法。用if-constexpr分支打印一次怎么样?@bipll是的,在这种情况下可以工作。我必须用if-constexpr将一堆SFINAE选择的方法组合成大的方法。不过,它确实可以编译和工作。我正在寻找一种方法,只选择编译器这不是正确的方法。我最终重构了我的代码,以更好地使用if-constexpr,这似乎是实现我所希望的最干净的方法。这很有效,也不算太遥远。我有几个布尔值我想使用,并希望避免将它们全部传入。如果我使用模板constexpr,我必须传入几个类型,这些类型仍将传递给ge这并不凌乱,但我想我可以缩短更复杂的表达式。这很管用,也不太遥远。我有几个布尔值我想使用,希望避免将它们全部传入。如果我使用模板constexpr,我必须传入几个类型,这仍然会变得凌乱,但我想我可以缩短更复杂的表达式。
#include <iostream>
#include <type_traits>

template <typename T>
struct Test
 {
   template <typename U>
   static constexpr bool is_array = std::is_array_v<U>;

   template <typename U = T,
             std::enable_if_t<not is_array<U>>* = nullptr>
   void print()
    { std::cout << "It's not an array\n"; }

   template <typename U = T,
             std::enable_if_t<is_array<U>>* = nullptr>
   void print()
    { std::cout << "It's an array\n"; }
 };

int main()
{
    Test<char[]>().print();
    Test<char>().print();
}
template <typename T>
struct Test
 {
   static constexpr bool is_array = std::is_array_v<T>;

   template <bool B = is_array,
             std::enable_if_t<not B>* = nullptr>
   void print()
    { std::cout << "It's not an array\n"; }

   template <bool B = is_array,
             std::enable_if_t<B>* = nullptr>
   void print()
    { std::cout << "It's an array\n"; }
 };