md-blog
md-blog copied to clipboard
当private继承时还是会有问题。
https://github.com/lexdene/md-blog/blob/master/cpp/is_derived_from/is_derived_from.md 在上面链接中,单例模式下仍有问题。 不如学/分析一下 is_base_of。
template <typename B, typename D>
struct Host {
operator B*() const;
operator D*();
};
template <typename B, typename D>
struct is_base_of {
private:
typedef char (&yes)[1];
typedef char (&no)[2];
template <typename T>
static yes check(D*, T);
static no check(B*, int);
public:
static const bool value = sizeof(check(Host<B, D>(), int())) == sizeof(yes);
};
struct Base {};
struct Derived : private Base {};
int main() {
static_assert(is_base_of<Base, Derived>::value, "Error");
is_base_of<Derived, Base>::value;
}
没说清楚,如果有
struct foo {};
struct bar : private foo {};
ConvertTester3<foo, bar>::test;
会编译出错。如果test为false的话,感觉会更好。
学习了。
不过能否解释一下,check函数为什么要有2个参数?我刚试了一下,发现把第2个参数删掉就不对了,但是不太明白为什么。
可以看一下这个。 http://stackoverflow.com/questions/2910979/how-does-is-base-of-work 第1个函数必须是模板,否则在2个类没有关系时会出现二义性。成为模板后,当发现有其他非模板函数可以匹配时,不考虑模板的版本,因而在这种情况下运行正确。 当2个类有关系时,由函数拾取规则得到会同时使用operator D*()这个转换函数,再由D类型更匹配static yes check(D, T);因而得到。如果没有第2个参数而又是模板的情况下,会因为无法推导出T类型而直接会被从candidates中去除,从而只能匹配第2个函数,根据条款4.10/3得到error.