检测来自父级的重载方法 class

Detecting overloaded method from parent class

我一直在使用下面的这个实用程序来检测成员方法是否已在 class 中定义,这在我的框架中的大多数情况下都有效。

template <typename C, typename TInput>
class HasHandle
{
    template <class T>
    static std::true_type testSignature(void(T::*)(const TInput&));

    template <class T>
    static decltype(testSignature(&T::HandleEvent)) test(std::nullptr_t);

    template <class T>
    static std::false_type                          test(...);

public:
    using type = decltype(test<C>(nullptr));
    static constexpr bool value = type::value;
};

但是当我尝试将一些共享 EventHandle 移动到基础 class 时,问题发生了,因此我可以在多个 class 中共享相同的事件处理逻辑。

将一些 EventHandle 移动到基础 class 并使用 using EventHandle 使基础 class 方法可见后,我注意到 HasHandle 将无法检测我在基础 class.

中定义的 EventHandle

这是一个简单的例子:

struct ShareEventHandler
{
    void HandleEvent(const int&) {}
};

struct Foo : public ShareEventHandler
{
    using ShareEventHandler::HandleEvent;
    void HandleEvent(const Foo&) {}
};

static_assert(HasHandle<Foo, Foo>::value, "failed to detect the method");
static_assert(HasHandle<Foo, int>::value, "failed to detect the method"); // this will fail

有没有人知道如何改进 HasHandle 来解决上面失败的 static_assert?


更新: 我使用的是 Microsoft Visual Studio Community 2019 Version 16.8.1,根据评论,该问题无法在 g++ 8.3.0 和 clang++ 7.0.1 上重现 这是编译测试的 link。 https://gcc.godbolt.org/z/1x9n3Y

删除 testSignature 的模板让所有编译器都满意:

template <typename C, typename TInput>
class HasHandle
{
    static std::true_type testSignature(void(C::*)(const TInput&));

    template <class T>
    static decltype(testSignature(&T::HandleEvent)) test(std::nullptr_t);

    template <class T>
    static std::false_type                          test(...);

public:
    using type = decltype(test<C>(nullptr));
    static constexpr bool value = type::value;
};

Demo