There's no way to do this in standard C++ alone. If you're using an implementation that has the Itanium C++ ABI1 you can do this though, for example:
#include <iostream>
#include <typeinfo>
#include <cxxabi.h>
#include <memory>
class base {
protected:
base() {
}
public:
static bool check(const std::type_info& p) {
// Find the real type_info for single inheritance non virtual
const __cxxabiv1::__si_class_type_info* test = dynamic_cast<const __cxxabiv1::__si_class_type_info*>(&p);
return test ? typeid(base) == *test->__base_type : false;
}
virtual ~base() {}
};
class der : public base {
};
class foo {};
int main() {
der d;
foo f;
std::cout << base::check(typeid(d)) << "\n";
std::cout << base::check(typeid(f)) << "\n";
}
Here this works because the type has a single, non-virtuallly inherited base. You can support more cases though with care and similar dynamic_casts
.
Whilst this is possible under these certain circumstances I think you're solving the wrong problem though - a solution based around a std::map
is more portable and avoids relying on implementation details like this.
1 confusingly named, it's a surprisingly large compiler/architecture list, not just Itanium