【发布时间】:2010-01-28 18:31:01
【问题描述】:
我真的对私有继承和受保护继承感到困惑。
1) 在受保护的继承中,公共成员和受保护成员成为派生类中的受保护成员。在私有继承中,一切都是私有的。但是,派生类永远不能访问基类的私有成员,对吗?在这两种情况下,派生类都可以访问公共成员和受保护成员。那正确吗?
2) 我注意到基类的私有成员永远不会被派生类触及。那么为什么私有成员会被继承呢?
【问题讨论】:
标签: c++
我真的对私有继承和受保护继承感到困惑。
1) 在受保护的继承中,公共成员和受保护成员成为派生类中的受保护成员。在私有继承中,一切都是私有的。但是,派生类永远不能访问基类的私有成员,对吗?在这两种情况下,派生类都可以访问公共成员和受保护成员。那正确吗?
2) 我注意到基类的私有成员永远不会被派生类触及。那么为什么私有成员会被继承呢?
【问题讨论】:
标签: c++
您在第 1 点上是正确的。从基类继承时指定private、protected 或public 不会更改派生类本身的任何访问方式。当派生类的实例在别处使用时,或者派生类碰巧用作其他类的基类时,这些访问说明符告诉编译器如何处理基类成员。
更新:以下内容可能有助于说明差异:
class Base
{
private: int base_pri;
protected: int base_pro;
public: int base_pub;
};
对于从基类派生的类:
class With_Private_Base : private Base { void memberFn(); };
class With_Protected_Base : protected Base { void memberFn(); };
class With_Public_Base : public Base { void memberFn(); };
// this would be the same for all of the above 3 classes:
void With_PXXX_Base::memberFn()
{
base_pri = 1; // error: `int Base::base_pri' is private
base_pro = 1; // OK
base_pub = 1; // OK
}
对于从 3 个派生类派生的类:
class A : public With_Private_Base { void memberFn(); }
void A::memberFn()
{
base_pri = 1; // error: `int Base::base_pri' is private
base_pro = 1; // error: `int Base::base_pro' is protected
base_pub = 1; // error: `int Base::base_pub' is inaccessible
}
class B : public With_Protected_Base { void memberFn(); }
void B::memberFn()
{
base_pri = 1; // error: `int Base::base_pri' is private
base_pro = 1; // OK
base_pub = 1; // OK
}
class C : public With_Public_Base { void memberFn(); }
void C::memberFn()
{
base_pri = 1; // error: `int Base::base_pri' is private
base_pro = 1; // OK
base_pub = 1; // OK
}
对前三个派生类的外部访问:
void main()
{
With_Private_Base pri_base;
pri_base.base_pri = 1; // error: `int Base::base_pri' is private
pri_base.base_pro = 1; // error: `int Base::base_pro' is protected
pri_base.base_pub = 1; // error: `int Base::base_pub' is inaccessible
With_Protected_Base pro_base;
pro_base.base_pri = 1; // error: `int Base::base_pri' is private
pro_base.base_pro = 1; // error: `int Base::base_pro' is protected
pro_base.base_pub = 1; // error: `int Base::base_pub' is inaccessible
With_Public_Base pub_base;
pub_base.base_pri = 1; // error: `int Base::base_pri' is private
pub_base.base_pro = 1; // error: `int Base::base_pro' is protected
pub_base.base_pub = 1; // OK
}
【讨论】:
1a) 受保护的继承意味着“子”可以访问它在公共继承中可以访问的所有内容,但使用该对象的其他人只能看到子的公共接口,其父级中的任何内容都被隐藏。
1b) 私有继承导致类的所有公共函数都被继承为私有函数 - 这意味着它们不能从子对象调用或从对象的客户端访问。
2) 私有成员被继承,因为基类中的方法可能需要它们来操作。
【讨论】:
是的,这是正确的。派生类可以访问其基类的受保护成员和公共成员,而派生类不能访问其基类的私有成员。
私有成员被继承的原因如下:基类可以定义一个受保护的或公共的函数来修改基类的私有成员。派生类可以调用这个函数,因此需要知道它正在访问的私有变量。
【讨论】:
1) 在受保护的继承中, 公共和受保护成员成为 派生中的受保护成员 班级。在私人继承中, 一切都是私人的。但是,那 派生类永远无法访问 基类的私有成员,是 对吗?
是的。
派生类可以 访问公众并受保护 两种情况下的成员。对吗?
是的。
2) 我注意到私人成员 基类的永远不会 被派生类触及。所以为什么 私有成员是否继承?
因为它们是基类的一部分,而您需要作为派生类一部分的基类。请注意,您仍然可以使用非重写的public/protected 成员函数来操作在基类中维护的某些状态(如果有)。
【讨论】:
1) 你是对的。没有任何类型的继承允许访问私有成员(只有 friend 声明允许)
2) 从某种意义上说,它们是“继承的”,即 Derived 类型的对象在存储在内存中时,包括 Derived 和 Base 的所有数据成员,包括 Base 的私有成员。私有成员不能消失,因为当 Base 的方法在该对象上运行时,它们将需要访问 Base 的私有成员。
此外,从技术上讲,Base 的私有成员的名称在 Derived 方法的范围内,但是如果您尝试访问它们当然会出现编译错误。
【讨论】: