在本文中,您将学习在C ++中使用公共继承,受保护继承和私有继承。您将通过示例学习在何处以及如何使用它。您可以从具有不同访问指定的基类声明一个派生类,即公共继承,受保护继承或私有继承。
#includeusing namespace std; class base { .... ... .... }; class derived : access_specifier base { .... ... .... };
注意:可以使用public,protected或private关键字代替上面代码中使用的access_specifier(访问说明符)术语。
派生类可以访问基类中所有的非私有成员。因此基类成员如果不想被派生类的成员函数访问,则应在基类中声明为 private。
我们可以根据访问权限总结出不同的访问类型,如下所示:
| 访问 | public | protected | private |
|---|---|---|---|
| 同一个类 | yes | yes | yes |
| 派生类 | yes | yes | no |
| 外部的类 | yes | no | no |
一个派生类继承了所有的基类方法,但下列情况除外:
基类的构造函数、析构函数和拷贝构造函数。
基类的重载运算符。
基类的友元函数。
当一个类派生自基类,该基类可以被继承为 public、protected 或 private 几种类型。继承类型是通过上面讲解的访问修饰符 access-specifier 来指定的。
我们几乎不使用 protected 或 private 继承,通常使用 public 继承。当使用不同类型的继承时,遵循以下几个规则:
公有继承(public):当一个类派生自公有基类时,基类的公有成员也是派生类的公有成员,基类的保护成员也是派生类的保护成员,基类的私有成员不能直接被派生类访问,但是可以通过调用基类的公有和保护成员来访问。
(1)基类的public和protected成员的访问属性在派生类中保持不变,但基类的private成员不可直接访问。
(2)派生类中的成员函数可以直接访问基类中的public和protected成员,但不能直接访问基类的private成员。
(3)通过派生类的对象访问从基类继承的成员,只能访问public成员。
示例:
- #include
-
- using namespace std;
-
- class CFather
- {
- public:
- int m_testA{0};
- protected:
- int m_testB{0};
- private:
- int m_testC{0};
- };
-
- class CSon: public CFather
- {
- void test()
- {
- m_testA = 1; // 编译正确 :public 继承后,在内部或者外部都可以访问public成员
- m_testB = 1; // 编译正确 :public 继承后,在内部可以访问protected成员
- m_testC = 1; // 编译错误 :无论哪种继承,都无法访问private成员
- }
- };
-
- int main()
- {
- CSon _test;
-
- _test.m_testA = 2; // 编译正确 :public 继承后,在内部或者外部都可以访问public成员
- _test.m_testB = 2; // 编译错误 :public 继承后,在外部无法访问protected成员
- _test.m_testC = 2; // 编译错误 :无论哪种继承,都无法访问private成员
-
- system("pause");
- return 0;
- }
保护继承(protected): 当一个类派生自保护基类时,基类的公有和保护成员将成为派生类的保护成员。
(1)基类的public和protected成员都以protected身份出现在派生类中,但基类的private成员`不可直接``访问。
(2)派生类中的成员函数可以直接访问基类中的public和protected成员,但不能直接访问基类的private成员。
(3)通过派生类的对象不能直接访问从基类继承的任何成员。
示例:
- #include
-
- using namespace std;
-
- class CFather
- {
- public:
- int m_testA{0};
- protected:
- int m_testB{0};
- private:
- int m_testC{0};
- };
-
- class CSon: protected CFather
- {
- void test()
- {
- m_testA = 1; // 编译正确 :protected 继承后,在内部可以访问public成员
- m_testB = 1; // 编译正确 :protected 继承后,在内部可以访问protected成员
- m_testC = 1; // 编译错误 :无论哪种继承,都无法访问private成员
- }
- };
-
- int main()
- {
- CSon _test;
-
- _test.m_testA = 2; // 编译错误 :protected 继承后,在外部无法访问public成员
- _test.m_testB = 2; // 编译错误 :protected 继承后,在外部无法访问protected成员
- _test.m_testC = 2; // 编译错误 :无论哪种继承,都无法访问private成员
-
- system("pause");
- return 0;
- }
此时,可以这么理解为 派生类 通过 protected继承 基类 之后 ,基类 中的 public变成了protected,其他保持原样。
- class CFather
- {
- protected:// proteced 继承之后public变成了 proteced
- int m_testA{0};
- protected:
- int m_testB{0};
- private:
- int m_testC{0};
- };
私有继承(private):当一个类派生自私有基类时,基类的公有和保护成员将成为派生类的私有成员。
(1)基类的public和protected成员都以private身份出现在派生类中,但基类的private成员不可直接访问。
(2)派生类中的成员函数可以直接访问基类中的public和protected成员,但不能直接访问基类的private成员。
(3)通过派生类的对象不能直接访问从基类继承的任何成员。
示例:
- #include
-
- using namespace std;
-
- class CFather // 基类
- {
- public:
- int m_testA{ 0 }; // 相当于int m_testA = 0;
- protected:
- int m_testB{ 0 };
- private:
- int m_testC{ 0 };
- };
-
- class CSon : private CFather // 私有继承(private)
- {
- void test()
- {
- m_testA = 1; // 编译正确 :private 继承后,在内部可以访问基类public成员
- m_testB = 1; // 编译正确 :private 继承后,在内部可以访问基类protected成员
- m_testC = 1; // 编译错误 :无论哪种继承,都无法访问基类private成员
- }
- };
-
- int main()
- {
-
- CSon _test;
-
- _test.m_testA = 2; // 编译错误 :private 继承后,在外部无法访问基类public成员
- _test.m_testB = 2; // 编译错误 :private 继承后,在外部无法访问基类protected成员
- _test.m_testC = 2; // 编译错误 :无论哪种继承,都无法访问基类private成员
-
- return 0;
- }
此时,可以这么理解为 派生类 通过 private继承 基类 之后 ,基类 中的 public与protected变成了private,其他保持原样。
- class CFather
- {
- private:// private 继承之后public变成了 private
- int m_testA{0};
- private:// private 继承之后protected变成了 private
- int m_testB{0};
- private:
- int m_testC{0};
- };
三者区别
public继承方式
基类中所有 public 成员在派生类中为 public 属性;
基类中所有 protected 成员在派生类中为 protected 属性;
基类中所有 private 成员在派生类中不能使用。
protected继承方式
基类中的所有 public 成员在派生类中为 protected 属性;
基类中的所有 protected 成员在派生类中为 protected 属性;
基类中的所有 private 成员在派生类中不能使用。
private继承方式
基类中的所有 public 成员在派生类中均为 private 属性;
基类中的所有 protected 成员在派生类中均为 private 属性;
基类中的所有 private 成员在派生类中不能使用。
多继承即一个子类可以有多个父类,它继承了多个父类的特性。
C++ 类可以从多个类继承成员,语法如下:
class <派生类名>:<继承方式1><基类名1>,<继承方式2><基类名2>,…
{
<派生类类体>
};
其中,访问修饰符继承方式是 public、protected 或 private 其中的一个,用来修饰每个基类,各个基类之间用逗号分隔,如上所示。现在让我们一起看看下面的示例:
- #include
- // 基类 Shape
- class Shape {
- public:
- void setWidth(int w) {
- width = w;
- }
-
- void setHight(int h) {
- height = h;
- }
-
- protected:
- int width;
- int height;
- };
-
- // 基类PaintCost
- class PaintCost {
- public:
- int getCost(int area) {
- return area * 70;
- }
- };
-
- // 派生类
- class Rectangle :public Shape, public PaintCost {
- public:
- int getArea() {
- return (width * height);
- }
- };
-
- int main() {
- Rectangle Rect;
- int area;
-
- Rect.setWidth(5);
- Rect.setHight(7);
-
- area = Rect.getArea();
-
- // 输出对象的面积
- std::cout << "总面积:" << Rect.getArea() << std:: endl;
-
- // 输出总花费
- std::cout << "总花费:¥" << Rect.getCost(area) << std::endl;
-
- return 0;
- }
输出结果:

部分参考自: