【发布时间】:2016-01-10 07:48:31
【问题描述】:
来自 C++ Primer 5th edition(D 继承自 B)
如果 D 使用 public 或 protected 从 B 继承,则从 D 派生的类的成员函数和朋友可以使用派生到基的转换。这样的 如果 D 从 B 私有继承,代码可能不会使用转换。
这有什么原因吗,还是我打算从表面上看?为什么会这样似乎很明显,但在一个例子中它让我绊倒了:
#include <iostream>
using namespace std;
class Base {
public:
int x = 2;
};
class Derived : protected Base { };
class DerivedAgain : public Derived {
friend void test();
};
void test() {
??? a;
Base* p = &a;
cout << p->x;
}
int main(){
test();
}
我想了解 test() 在派生到基础的转换中对成员 x 的可访问性。考虑函数test() 中a 类型??? 的三种潜在情况。
-
???是Base。x是Base的公共成员。在这种情况下没有问题。 -
???是DerivedAgain。在这种情况下,Derived-to-Base 转换是有意义的,因为test()具有friend对DerivedAgain的所有成员的访问权,包括从Base间接继承的那些成员。所以使用指针访问x没有问题。 -
???是Derived。它编译得很好。但为什么?在这一点上我很困惑。test()没有对Derived类成员的特殊访问权限,那么为什么p->x应该工作,因此派生到基的转换是有效的?只是因为它起作用吗?
如果我将test()的操作改为
void test() {
Derived a;
cout << a.x;
}
它无法编译,正如我所期望的那样 - 因为 Derived 对象继承的 x 成员被设为 protected,因此不能被用户使用。
如果我用Base 和DerivedAgain 替换a 的类型,修改后的test() 可以正常编译,正如我所期望的那样。
如果第二级派生类的友元函数没有对第一级派生的特殊访问权限,为什么允许第二级派生类的友元函数使用第一级直接到基数转换,我只是感到困惑班级成员。
【问题讨论】:
标签: c++ inheritance friend