Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/templates/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 如何实现is_多态函数?_C++_Templates_C++11_Metaprogramming_Decltype - Fatal编程技术网

C++ 如何实现is_多态函数?

C++ 如何实现is_多态函数?,c++,templates,c++11,metaprogramming,decltype,C++,Templates,C++11,Metaprogramming,Decltype,我正在尝试实现is_polymorphic_functor元函数,以获得以下结果: //non-polymorphic functor template<typename T> struct X { void operator()(T); }; //polymorphic functor struct Y { template<typename T> void operator()(T); }; std::cout << is_polymorphic_f

我正在尝试实现
is_polymorphic_functor
元函数,以获得以下结果:

//non-polymorphic functor
template<typename T> struct X { void operator()(T); };

//polymorphic functor 
struct Y { template<typename T> void operator()(T); };

std::cout << is_polymorphic_functor<X<int>>::value << std::endl; //false
std::cout << is_polymorphic_functor<Y>::value << std::endl; //true
它试图利用
functor\u traits
的以下实现:

//functor traits
template <typename T>
struct functor_traits : functor_traits<decltype(&T::operator())>{};

template <typename C, typename R, typename... A>
struct functor_traits<R(C::*)(A...) const> : functor_traits<R(C::*)(A...)>{};

template <typename C, typename R, typename... A>
struct functor_traits<R(C::*)(A...)>
{
   static const size_t arity = sizeof...(A) };

   typedef R result_type;

   template <size_t i>
   struct arg
   {
      typedef typename std::tuple_element<i, std::tuple<A...>>::type type;
   };
};
如何解决此问题并使
多态函数是否按预期工作

这对我很有用:

template<typename T>
struct is_polymorphic_functor
{
private:
    //test if type U has operator()(V)
    template<typename U, typename V>
    static auto ftest(U *u, V* v) -> decltype((*u)(*v), char(0));
    static std::array<char, 2> ftest(...);

    struct private_type { };

public:
    static const bool value = sizeof(ftest((T*)nullptr, (private_type*)nullptr)) == 1;
};
模板
结构是多态函子
{
私人:
//测试U型是否有运算符()(V)
模板
静态自动ftest(U*U,V*V)->decltype((*U)(*V),char(0));
静态std::数组ftest(…);
结构私有_类型{};
公众:
静态常量布尔值=sizeof(ftest((T*)nullptr,(private_type*)nullptr))=1;
};

假设非多形函子没有重载的
运算符()

模板
类是\u多态\u函子{
模板
静态constexpr bool get(int){return false;}
模板
静态constexpr bool get(…){return true;}
公众:
静态constexpr bool value=get(0);
};

在第二个“过载”被测试的地方,如果没有T,那么每种类型都会发生第一个过载。

Er,SFINAE?它与您自己的代码没有什么不同,所以我不确定您不理解的是什么。如果它被定义为
template void operator()(t…)
,那么它已经起作用了。其他测试失败:@Nawaz这几乎是,但不完全是,与您最初的请求完全不同。@Nawaz:而且我们不可能在SO答案中包含所有可能的编程代码。可以肯定的是,使用半固定签名(如
polymorphic2
)测试任意数量的函数实际上是不可能的,但我看不到它的用例。如果您还不知道签名,它将提供什么有用的信息呢?那么,
struct test{void operator()(int){};void operator()(double){};}是多态的,但它是
结构疯狂{template typename std::enable_if::type operator()(T){};}多态?我怀疑你已经请人解决了停车问题。令人惊叹的。已通过所有测试用例:@Nawaz:如果这些“测试用例”很重要,请将它们添加到您的问题中多态?:)这不会测试类是否具有多态运算符(),只测试它没有非多态运算符。
error: decltype cannot resolve address of overloaded function
template<typename T>
struct is_polymorphic_functor
{
private:
    //test if type U has operator()(V)
    template<typename U, typename V>
    static auto ftest(U *u, V* v) -> decltype((*u)(*v), char(0));
    static std::array<char, 2> ftest(...);

    struct private_type { };

public:
    static const bool value = sizeof(ftest((T*)nullptr, (private_type*)nullptr)) == 1;
};
template<typename T>
class is_polymorphic_functor {
  template <typename F, typename = decltype(&F::operator())>
  static constexpr bool get(int) { return false; }
  template <typename>
  static constexpr bool get(...) { return true; }

public:
  static constexpr bool value = get<T>(0);
};
template<template<typename>class arbitrary>
struct pathological {
  template<typename T>
  typename std::enable_if< arbitrary<T>::value >::type operator(T) const {}
};
template<template<typename>class arbitrary>
struct pathological2 {
  void operator()(int) const {}
  template<typename T>
  typename std::enable_if< arbitrary<T>::value >::type operator(T) const {}
};