C++ 为啥要使用公有、私有或受保护的继承?

Posted

技术标签:

【中文标题】C++ 为啥要使用公有、私有或受保护的继承?【英文标题】:C++ why use public, private or protected inheritance?C++ 为什么要使用公有、私有或受保护的继承? 【发布时间】:2013-01-03 01:41:06 【问题描述】:

关于这个主题有足够的信息。例如这个线程对我来说很清楚:Difference between private, public, and protected inheritance

除了一点;为什么有用?

【问题讨论】:

要回答一半的问题,请参阅***.com/questions/656224/… 另外,***.com/questions/374399/… 【参考方案1】:

这都是关于数据封装

http://en.wikipedia.org/wiki/Encapsulation_(object-oriented_programming)

Encapsulation concept

最好保护您的类的“内部”数据免受其他类的影响。好处包括:

其他类必须通过已知的适当访问机制(例如方法)来访问您的类,并且不能直接与您的类的内部进行胡闹(因此可能会使您的类进入一些未知和损坏的状态) 您可以更改班级的内部运作,并知道其他班级不会因此而中断 减少与课程的可见外部接触点,使您的课程更易于使用和理解

选择使用protected 而不是private 也可以让您的代码更容易通过子类化进行扩展。

【讨论】:

【参考方案2】:

使用 公共继承 来反映 is-a 关系。这是继承的主要用途,尤其是与虚函数结合使用。它允许重用接口,不仅是新代码重用旧代码,还允许旧代码重用新代码! (因为在运行时分派虚函数)。

在特殊情况下,使用私有继承来反映is-implemented-in-terms-of 关系。这是一种经常被过度使用的模式,通常可以通过组合(将可能的基类作为数据成员)来达到相同的目标。另一个缺点是您可以轻松地对同一个基类进行多重继承(删除两次或多次),从而导致所谓的Diamond Problem。

避免使用受保护的继承,这表明您的类接口依赖于客户端(派生类与世界)。这通常是由于类具有多种职责,建议将其重构为单独的类是合适的。

【讨论】:

两次或多次删除”什么意思? @curiousguy 我的意思是两个类之间的继承级别数。 D : B 被删除后,D1 : BD2 : BE : D1, D2 是所谓的菱形,其中一个类继承自两个类,每个类都继承自同一个类。 E 在此处从 B 中删除了两次。【参考方案3】:

这个问题的答案是关于类接口和数据封装,而不是语言能力。

受保护和私有继承的用例相当有限,因为通常有其他可用选项可以更好地解决问题(例如使用组合,而不是继承)。但是,有时您必须必须从某种类型继承(例如与第三方库接口),但您会强烈更喜欢(出于与您的类的用户界面)以隐藏从您的新类型用户继承的大多数从基类继承的成员。一个典型的场景是当您需要您的类型具有某个类的成员函数以供内部使用时,但是如果从类本身外部调用它会破坏您的新类型的逻辑。

在这些情况下,您需要使用privateprotectedinheritance(取决于接口是否应类似地限制为进一步的派生类。

但是请记住,这只是(强烈)向您的班级的用户暗示他们应该如何使用它。您正在调整其公共接口以隐藏其基类中公开的某些功能。严格来说,这并不能阻止人们访问这些成员,因为任何人仍然可以将指向派生类的指针转换为指向基类的指针,并以这种方式访问​​“隐藏”资源。

【讨论】:

【参考方案4】:

私有:类的私有成员只能从类函数、构造函数和析构函数中访问。将使用您的课程的客户将无法访问它们。因此,例如,如果您正在实现一个列表类并且想要跟踪列表的大小,那么您应该有一个私有变量(例如listSizeP)。您这样做是因为您不希望客户端能够在不插入元素的情况下修改列表的大小。

公共:公共成员也可以被客户端访问。在上面提到的列表示例中,inserterase 等函数应该是公共的。

Protected:类的protected成员,和private成员一样,只能从类函数中访问,但也可以被该类继承的类访问(其实这取决于派生类继承基类,如果不是公有继承,那么派生类就不能访问基类的私有成员,所以最常见的继承方式是公有继承)。示例:

#include <iostream>

using namespace std;

class Base 
public:
    int num;
public:
    Base(int x=0) : num(x) 
;

class Derived : public Base 
public:
    Derived(int x=0) : Base(x) 
    void tell()  cout << "num: " << num << endl; 
;

int main() 
    Derived D(4);
    D.tell(); // would cause error if num was private
    return 0;

【讨论】:

以上是关于C++ 为啥要使用公有、私有或受保护的继承?的主要内容,如果未能解决你的问题,请参考以下文章

回顾C++:访问权限控制之 公有保护私有继承用法详解与总结

C++多继承

私有继承、公有继承和受保护继承之间的区别

私有继承、公有继承和受保护继承之间的区别

c++ public,protected,private

❥关于C++之私有继承