【问题标题】:Why SFINAE doesn't work?为什么 SFINAE 不起作用?
【发布时间】:2017-07-29 18:52:59
【问题描述】:

我想检查这个类是否有operator()。 我尝试了以下 SFINAE。

#include <type_traits>  //for std::true_type/false_type
#include <utility>      //for std::declval

template <typename T, typename... A>
class has_call_operator {
private:
    template <typename U, typename... P>
    static auto check(U u, P... p) -> decltype(u(p...), std::true_type());
    static auto check(...) -> decltype(std::false_type());

public:
    using type
        = decltype(check(std::declval<T>(), std::declval<A>()...));
    static constexpr bool value = type::value;
};

乍一看,这工作正常。

#include <iostream>

struct test {
    void operator()(const int x) {}
};

int main()
{
    std::cout << std::boolalpha << has_call_operator<test, int>::value << std::endl;    //true
    return 0;
}

但是,抽象类并不能正常工作。

#include <iostream>

struct test {
    void operator()(const int x) {}
    virtual void do_something() = 0;
};

int main()
{
    std::cout << std::boolalpha << has_call_operator<test, int>::value << std::endl;    //false
    return 0;
}

为什么这段代码不起作用? 另外,你能让这段代码工作吗?

【问题讨论】:

    标签: c++ sfinae


    【解决方案1】:

    您按值获取U,因此它还需要类型的构造。

    通过 const 引用来解决这个问题。

    你可以看看is_detected 并有类似的东西:

    template <typename T, typename ...Ts>
    using call_operator_type = decltype(std::declval<T>()(std::declval<Ts>()...));
    
    template <typename T, typename ... Args>
    using has_call_operator = is_detected<call_operator_type, T, Args...>;
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多