前言
在本篇文章中我们将会学到有关继承方面的知识,其中C++中三大特性分别为:封装,继承多态。由此可见继承在学习中的重要性,接下来我们来一起看一下有关继承方面的知识吧!!!!😘 😚😘 😚😘 😚
一、继承的概念
继承是一种代码复用的重要手段,在保证原有类的基础上,再增加一下新的功能,成为一个新的类。
🌟🌟我们来举个例子,比如人,在学校分为很多类型,比如学生,老师。那他们有什么共同点信息呢?就比如:都具有姓名,年龄,身高,体重等。
但是我们会发现,我们每个学生都具有学号,而老师具有的是教职工号。
前面的大部分属性都相同,唯独学号,教职工号这一点不同,那如果我们写成两个类,就会出现很多重复的数据。
这时,继承就出现了。
继承:将相同的属性放置到父类中,自己独有的放在子类中
其中父类也称为基类,子类也称为派生类
继承呈现出面向对象程序设计的层次结构,继承是类设计层次的复用。
🌟🌟我们来看一下子类是如何定义的呢
class Person
{
public:
void Print()
{
cout << "name:" << _name << endl;
cout << "age:" << _age << endl;
}
protected:
string _name = "peter"; // 姓名
int _age = 18; // 年龄
};
class Student : public Person
{ }
class/struct 派生类 : 继承方式 基类
我们定义两个看一下
class Teacher :public Person
{
public:
protected:
int _teaid;//教职工号
};
class Student :public Person
{
public:
protected:
int _stuid;//教职工号
};
继承后的子类拥有父类的成员方法和成员变量
🌟🌟我们调用看一下
print函数是在Person类中实现的,但是Student和Teacher类继承了Person类,拥有了Person类的成员变量和成员方法。
🌟🌟我们在实现子类的方法中,派生类和基类我们都可以理解,但是这个继承方法是什么呢???我们接下来看一张表格理解一下。
🔱我们先来看一下,最后一行,在派生类中都是不可见的。那不可见是什么意思呢??
父类中的private成员和方法,虽然可以继承给子类,但是在子类中是不可以使用和访问的。
那麽看起来,这个private好像没什么用了,我们都不能使用还定义它干什么。确实是这样,我们今后在学习中,一般都不采用private.
🔱我们不使用private,那父类中的成员变量就全部暴漏给外边了,可以随便访问修改,那不就符合我们封装的意义了。我们引入了一个新的关键字:protected。它允许子类中的成员访问,但不允许外边的进行访问。
🔱class中默认是private的,struct中默认是public的,我们建议都写上。
🔱基类的私有成员在子类都是不可见。基类的其他成员在子类的访问方式 == Min(成员在基类的访问限定符,继承方式),public > protected> private。
我们一般使用:父类中使用public和protected定义变量和方法。子类继承方法采用public继承。
二、基类和派生类对象赋值转换
子类成员可以赋值给父类成员,但是父类成员不可以赋值给子类成员。
父类赋值给子类一般都是这样,但是有特殊情况,基类的指针或引用可以通过强制类型转换赋值给派生类指针或者引用。
但是必须是基类的指针是指向派生类对象才是安全的。这里的基类如果是多态类型,可以使用dynamic_cast识别后进行安全转换。
派生类对象 可以赋值给 基类的对象 / 基类的指针 / 基类的引用。这里有个形象的说法叫切片或者切割。寓意把派生类中父类那部分切来赋值过去
Student s1;
//派生类对象赋值给基类对象
Person p1 = s1;
//派生类对象赋值给基类引用
Person &p1 = s1;
//派生类对象赋值给基类指针
Person *p1 =& s1;
我们看一下底层逻辑,子类在赋值给父类时,子类的变量多赋值就会发生切片。
这其中不会产生临时变量
三、继承中的作用域,隐藏
父类和子类拥有不同的作用域
那就这就说明父类和子类可以有相同的成员变量和成员方法,但是我们在日常生活中一般不建议这样使用,但是考试题目中及其喜欢出这样的题目。
🌟🌟我们看一下下面这个例子
class Person
{
protected :
string _name = "小李子"; // 姓名
int _num = 111; // 身份证号
};
class Student : public Person
{
public:
void Print()
{
cout<<" 姓名:"<<_name<< endl;
cout<<" 学号:"<<_num<<endl;
}
protected:
int _num = 9