继续尝试理解std :: enable_if用法

时间:2018-04-09 06:41:01

标签: c++14 sfinae

在这段代码中:

#include <iostream>
#include <cstdlib>
#include <type_traits>
#include <ios>

using std::enable_if;
using std::is_same;
using std::boolalpha;
using std::cout;
using std::endl;

template <typename T>
struct S {
  S(): t(static_cast<T>(NULL)) { }

  // void type() {
  //   cout << boolalpha;
  //   cout << is_same<T,int>::value << endl;
  // }

  template <typename enable_if<is_same<T,int>::value,T>::type>
  void type() {
    cout << boolalpha << true << endl;
  }

  T t;
};

int main(){
  S<int> s;
  s.type();
  return(0);
}

我获得了作为非模板函数实现的方法type()的成功编译和输出;但是,对于使用std::enable_if实现为模板函数的相同方法,我得到以下编译错误:

so_main.cpp:23:11: error: no matching member function for call to 'type'
        s.type();
        ~~^~~~
so_main.cpp:15:73: note: candidate template ignored: couldn't infer template argument ''
        template<typename enable_if<is_same<T,int>::value,T>::type>void type(){cout << boolalpha << true << endl;}
                                                                        ^
1 error generated.

我的理解是两种情况下实施的逻辑是相似的。 当该方法为非模板时,T的类型将被确认为int。但是,如果std::enable_if用于为相同条件启用模板函数(即Tint),则代码不会编译。

1 个答案:

答案 0 :(得分:1)

这是因为SFINAE仅适用于与模板本身相关的模板参数。标准称为直接上下文。在您的代码示例中,EWOULDBLOCK是类模板的模板参数,而不是成员函数模板的模板参数。

您可以通过为您的函数提供一个默认为T的虚拟模板参数,并在其上使用SFINAE来解决此问题,如下所示:

T