#include <iostream>
#include <type_traits>
class A {};
class B : public A {};
class X {};
class Y : public X {};
class Other {};
template <typename Param, std::enable_if_t<std::is_base_of<A, Param>::value, bool> = true>
void doStuff() { std::cout << "Base A" << std::endl; }
template <typename Param, std::enable_if_t<std::is_base_of<X, Param>::value, bool> = true>
void doStuff() { std::cout << "Base X" << std::endl; }
template <typename Param, std::enable_if_t<!(std::is_base_of<A, Param>::value || std::is_base_of<X, Param>::value), bool> = true>
void doStuff() { std::cout << "Something else" << std::endl; }
int main()
{
doStuff<B>();
doStuff<Y>();
doStuff<Other>();
}
I2luY2x1ZGUgPGlvc3RyZWFtPgojaW5jbHVkZSA8dHlwZV90cmFpdHM+CgpjbGFzcyBBIHt9OwoKY2xhc3MgQiA6IHB1YmxpYyBBIHt9OwoKY2xhc3MgWCB7fTsKCmNsYXNzIFkgOiBwdWJsaWMgWCB7fTsKCmNsYXNzIE90aGVyIHt9OwoKdGVtcGxhdGUgPHR5cGVuYW1lIFBhcmFtLCBzdGQ6OmVuYWJsZV9pZl90PHN0ZDo6aXNfYmFzZV9vZjxBLCBQYXJhbT46OnZhbHVlLCBib29sPiA9IHRydWU+CnZvaWQgZG9TdHVmZigpIHsgc3RkOjpjb3V0IDw8ICJCYXNlIEEiIDw8IHN0ZDo6ZW5kbDsgfQoKdGVtcGxhdGUgPHR5cGVuYW1lIFBhcmFtLCBzdGQ6OmVuYWJsZV9pZl90PHN0ZDo6aXNfYmFzZV9vZjxYLCBQYXJhbT46OnZhbHVlLCBib29sPiA9IHRydWU+CnZvaWQgZG9TdHVmZigpIHsgc3RkOjpjb3V0IDw8ICJCYXNlIFgiIDw8IHN0ZDo6ZW5kbDsgfQoKdGVtcGxhdGUgPHR5cGVuYW1lIFBhcmFtLCBzdGQ6OmVuYWJsZV9pZl90PCEoc3RkOjppc19iYXNlX29mPEEsIFBhcmFtPjo6dmFsdWUgfHwgc3RkOjppc19iYXNlX29mPFgsIFBhcmFtPjo6dmFsdWUpLCBib29sPiA9IHRydWU+CnZvaWQgZG9TdHVmZigpIHsgc3RkOjpjb3V0IDw8ICJTb21ldGhpbmcgZWxzZSIgPDwgc3RkOjplbmRsOyB9CgppbnQgbWFpbigpCnsKICAgIGRvU3R1ZmY8Qj4oKTsKICAgIGRvU3R1ZmY8WT4oKTsKICAgIGRvU3R1ZmY8T3RoZXI+KCk7Cn0=