一文搞懂C++继承、多继承、菱形继承、虚继承
继承目录
[*]继承
[*]继承
[*]继承的访问权限
[*]子类赋值给父类
[*]赋值兼容规则
[*]“自然”的行为
[*]验证:
[*]1. 其他权限继承可否支持赋值兼容规则
[*]2.是否"自然",有没有产生临时变量
[*]继承中的作用域
[*]继承的构造函数
[*]继承的拷贝构造
[*]继承的operator=
[*]继承的析构函数
[*]析构次序
[*]析构的特别处理惩罚
[*]继承中的static成员
[*]设计一个不能被继承的类
[*]多继承
[*]菱形继承
[*]定义
[*]标准的菱形继承图:
[*]菱形继承的二义性和数据冗余
[*]代码举例:
[*]菱形继承的现实问题:
[*]菱形继承的内存布局
[*]解决数据冗余 -- 虚继承
[*]定义:
[*]用法:
[*]示例代码:
[*]VS监视窗口现象
[*]虚继承的原理
[*]留下问题:
[*]成本优势
[*]虚继承的特性
[*]练习题
[*]模型图
[*]补充注意
[*]继承和组合
继承
[*]继承受权限影响
有public protected private 三种继承
[*]基本语法:
class 子类 : 权限 父类
class student : public Person
[*]使用父类成员的方法
使用域作用限定符显式指出,语法:
基类::基类成员
Person::Print();
[*]继承方式也可以不写 -- 默认是public,发起显式写出继承方式
a.对于class,默认继承方式是私有
b.对于struct默认继承方式是公有
[*]继承可以以为是将父类看成子类的一个看不见成员
证明:
https://img2023.cnblogs.com/blog/2921710/202405/2921710-20240530175509723-259472899.png
[*]友元关系不能被继承
父类的友元不是子类的友元.友元只对所在的类域有效
继承的访问权限
继承的访问权限的作用是将继承下来的父类成员的原有的权限进行缩小.
类权限
[*]public: 外部,子类都可见
[*]protected: 外部不可见,子类可见
[*]private: 外部,子类都不可见
[*]继承的访问权限表
类成员\继承方式public继承protected继承private继承基类的public成员派生类的public成员派生类的protected成员派生类的private成员基类的protected成员派生类的protected成员派生类的protected成员派生类的private成员基类的private成员在派生类中不可见在派生类中不可见在派生类中不可见基类的private成员最特别,继承后子类不可见. 其他权限成员无论被什么方式继承至少子类本身内部可见
[*]继承的权限可以被缩小,但是不能放大,和const一样
[*]私有继承私有成员也是继承下来了,只是对子类和外界都不可见(直接不可见). 虽然子类不可见,但是可以通过父类的方法间接去调用(间接可见)
子类赋值给父类
赋值兼容规则
在公有继承中,子类可以赋值给父类 并且是自然支持(编译器直接行为),没有临时变量,(不是隐式类型转换,不存在类型转换发生)
[*]派生类的对象可以赋值给基类对象。
[*]派生类的对象可以初始化基类的引用。
[*]派生类对象的地址可以赋给指向基类的指针。
“自然”的行为
“赋值”过程是通过切片方式,通过调用父类拷贝构造/赋值运算符重载完成赋值,将从父类继承下的部分依次赋值给父类,
引用和指针也是类似,通过切片方式,直接引用/指向子类中父类的一部分,也是"自然"的,不存在类型转换的发生
切片不是丢弃,是分别
验证:
1. 其他权限继承可否支持赋值兼容规则
class Person{public: Person(std::string name, int age) :_name(name), _age(age) {}; void Print(){ std::cout
页:
[1]