这被认为是SFINAE吗?

Me *_*d I 10 c++ sfinae c++11

我在一周前询问了一个问题,询问如何只在它所采用的类型具有特定成员函数时才能简单地实例化一个类模板.在我的回答中,我得到了一个复杂的解决方案.但后来我试着自己做.我只是想知道这是否足以弄清楚给定类型T是否有一个名为ftake 0参数的void函数.

#include <type_traits>
#include <utility>

template <typename T, typename = void>
struct has_f : std::false_type { };

template <typename T>
struct has_f<
    T,
    decltype(std::declval<T>().f(), void())> : std::true_type { };

template <typename T, typename = typename std::enable_if<has_f<T>::value>::type>
struct A { };

struct B
{
    void f();
};

struct C { };

template class A<B>; // compiles
template class A<C>; // error: no type named ‘type’ 
                     // in ‘struct std::enable_if<false, void>’
Run Code Online (Sandbox Code Playgroud)

如果是这样,为什么其他答案在这个帖子中如此复杂

Pot*_*ter 7

是的,你已经用最简单,最惯用的C++ 11 SFINAE风格解决了它.

请注意,您没有检查返回类型void,它是非静态成员,也没有参数.f只是可调用而没有参数.它甚至可以是一个仿函数.

要检查返回的Nullary成员非静态函数void,请使用

template <typename T>
struct has_f<T, decltype(void( static_cast< void (T::*)( void ) >( &T::f ) )) >
    : std::true_type {};

template <typename T>
struct has_f<T, decltype(void( static_cast< void (T::*)( void ) const >( &T::f ) )) >
    : std::true_type {};
Run Code Online (Sandbox Code Playgroud)