I was having an issue with std::is_base_of
being called inside of a class declaration for an incomplete type. I came across this StackOverflow question: Why can't "is_base_of" be used inside a class declaration (incomplete type)?
Then I tried to implement my own metafunction for checking if the given template class is base of another.
I have tested my code with C++17
on MSVC 19.28.29337
(version reported by cl.exe
) and on clang-7
online compiler, and seems it works perfectly both for complete and incomplete classes. Here is my code:
namespace helper {
template<class Base>
static std::true_type isBaseOf(Base *b);
template<class Base>
static std::false_type isBaseOf(...);
template<class Base>
static std::false_type isBaseOf(void*);
}
template<class B, class D>
using IsBaseOf = decltype(helper::isBaseOf<B>(std::declval<D*>()));
template<class B, class D>
static inline constexpr bool IsBaseOf_v = IsBaseOf<B, D>::value;
Now I am wondering, what is wrong with my code? Isn't it portable? Doesn't it conform to the standard? Have I done something unacceptable?
Also, if everything is ok with my code, then why is the standard not using such a simple implementation?
Added handling for void
type - thanks to Scheff.
Seems the only difference is that it does not handle non-public inheritance.
Thanks to Axalo for the comment