派生类可以继承定义在基类中的成员,但是派生类的成员函数不一定有权访问从基类继承而来的成员。
派生类将除了基类的构造函数和析构函数以外的所有成员都继承下来了。
类的public、protected、private继承
/ | public继承 | protected继承 | private继承 |
---|---|---|---|
基类public成员 | public | protected | 不可见 ❌ |
基类protected成员 | protected | protected | 不可见❌ |
基类private成员 | public | protected | 不可见❌ |
1.公有继承的特点是:基类的公用成员和保护成员在派生类中保持原有的访问属性,其私有成员仍为基类私有,即在派生类中不能访问,在类外也不能访问。
私有成员体现了数据的封装性,如果基类的私有成员可以被派生类所访问,即破坏了基类的封装性,这就会失去C++的一个重要特性。
为什么派生类不能访问基类的私有成员?
答:因为派生类和基类是不同的类域,在不同类中访问相当于在类外访问私有成员。
我们在派生类的成员函数中访问了父类的私有成员,相当于在类外访问私有成员,是错误的。
2.保护继承的特点是:基类的所有公有成员和保护成员都成为派生类的保护成员,并且只能被它的派生类成员函数或友元访问,基类的私有成员仍然是私有的。
原public,protected属性的成员继承后为protected属性,原private成员仍为private属性
The protected access label can be thought of as a blend of private and
public : Like private members, protected members are inaccessible to
users of the class. Like public members, the protected members are
accessible to classes derived from this class.
portected成员在基类内表现类似private成员(可以在基类内被访问,不可以在基类外[对象]被访问),在基类被public/protected继承时表现类似public成员(可以在派生类内被访问,不可以在派生类外[对象]被访问);
3.私有继承的特点:即所有基类成员均变成派生类的私有成员,基类的私有成员仍然不能在派生类中访问。
三种继承方式都介绍完毕后,肯定会有一个问题,那就是派生类无论怎样都无法访问基类的私有成员,那么我们要想知道私有成员的状态应该怎么办呢?
我们可以在基类定义非私有的show函数,然后在派生类调用它即可
public继承:基类public、protected、private的访问权限
/ | 基类内 | 基类对象 | 派生类内 | 派生类对象 |
---|---|---|---|---|
基类public成员 | ✅ | ✅ | ✅ | ✅ |
基类protected成员 | ✅ | ❌ | ✅ | ❌ |
基类private成员 | ✅ | ❌ | ❌ | ❌ |
#include<iostream>
using namespace std;
//////////////////////////////////////////////////////////////////////////
class A //父类
{
private:
int privatedateA;
protected:
int protecteddateA;
public:
int publicdateA;
};
//////////////////////////////////////////////////////////////////////////
class B :public A //基类A的派生类B(继承)
{
public:
void funct()
{
int b;
b=privatedateA; //error:基类中私有成员在派生类中是不可见的
b=protecteddateA; //ok:基类的保护成员在派生类中为保护成员
b=publicdateA; //ok:基类的公共成员在派生类中为公共成员
}
};
//////////////////////////////////////////////////////////////////////////
class C :private A //基类A的派生类C(私有继承)
{
public:
void funct()
{
int c;
c=privatedateA; //error:基类中私有成员在派生类中是不可见的
c=protecteddateA; //ok:基类的保护成员在派生类中为私有成员
c=publicdateA; //ok:基类的公共成员在派生类中为私有成员
}
};
//////////////////////////////////////////////////////////////////////////
class D :protected A //基类A的派生类D(保护继承)
{
public:
void funct()
{
int d;
d=privatedateA; //error:基类中私有成员在派生类中是不可见的
d=protecteddateA; //ok:基类的保护成员在派生类中为保护成员
d=publicdateA; //ok:基类的公共成员在派生类中为保护成员
}
};
//////////////////////////////////////////////////////////////////////////
int main()
{
int a;
B objB;
a=objB.privatedateA; //error:基类中私有成员在派生类中是不可见的,对对象不可见
a=objB.protecteddateA; //error:基类的保护成员在派生类中为保护成员,对对象不可见
a=objB.publicdateA; //ok:基类的公共成员在派生类中为公共成员,对对象可见
C objC;
a=objC.privatedateA; //error:基类中私有成员在派生类中是不可见的,对对象不可见
a=objC.protecteddateA; //error:基类的保护成员在派生类中为私有成员,对对象不可见
a=objC.publicdateA; //error:基类的公共成员在派生类中为私有成员,对对象不可见
D objD;
a=objD.privatedateA; //error:基类中私有成员在派生类中是不可见的,对对象不可见
a=objD.protecteddateA; //error:基类的保护成员在派生类中为保护成员,对对象不可见
a=objD.publicdateA; //error:基类的公共成员在派生类中为保护成员,对对象不可见
return 0;
}
public继承 是一个接口继承,保持is-a原则,每个父类可用的成员对子类也可用,因为每个子类对象也都是一个父类对象。
protetced继承 / private继承 是一个实现继承,基类的部分成员并非完全成为子类接口的一部分,是 has-a 的关系原则。
参考链接
https://blog.csdn.net/lixungogogo/article/details/51134157
https://blog.csdn.net/feiyinzilgd/article/details/6226348
https://www.cnblogs.com/qlwy/archive/2011/08/25/2153584.html