C++继承 之 菱形继承


前言

  • 之前我们面对的都是一对一的单继承,那么我们这次来看一下多继承以及菱形继承吧~~~
  • 环境:VS2019版本


1、单继承和多继承

1.1、概念

1.1.1、单继承

单继承一个子类只有一个直接父类时,成这种继承关系为单继承

class Person
{
};
class Student:public Person//Student类直接单继承Person类
{
};
class PostGraduate:public Student//PostGraduate类直接单继承Student类
{
};

以上代码均属于单继承关系
图形表示形式:
在这里插入图片描述

1.1.2、多继承

多继承一个子类有两个或两个以上的直接父类时,称这种继承关系为多继承

class Student 
{
public:
	int _s;
};
class Teacher
{
public:
	int _t;
};
class Assistant:public Student , public Teacher
//Assistant类多继承于Student类和Teacher类
{
	int _a;
};

如下图则是一种多继承关系
在这里插入图片描述

  • 1.再多继承情况下,子类继承每个基类的继承访问权限不能少!!!(否则编译器将视为默认继承权限:private

以实例代码为例(Teacher类前未显示public继承权限):
在这里插入图片描述

  • 2.多继承情况下,各个类的数据的存储顺序与继承列表中的顺序保持一致
    以实例代码为例
int  main()
{
	Assistant a;
	a._s = 1;
	a._t = 2;
	a._a = 3;

	return 0;
}

在这里插入图片描述
由此也可得到多继承的对象模型为:
在这里插入图片描述

2、菱形继承

2.1、概念

菱形继承:菱形继承是多继承的一种特殊情况,也可视为单继承和多继承的结合


class B {
public:
	
	int _b;
};
class C1 :public B
{
public:
	int c1;
};
class C2 :public B
{
public:
	int c2;
};
class D :public C1, public C2
{
	int _d;
};

如下图:
在这里插入图片描述

2.2、 存在的问题

以上述实例代码为例
在这里插入图片描述
底层子类对最顶层的基类成员赋值将出现不明确问题!!
原因:C1和C2类都继承了B类中的成员_b,因而子类D类对象d在对_b赋值时无法判断是对C1类中的_b赋值还是对C2类中的_b赋值

  • 从中也可看出菱形继承中所存在的数据冗余以及二义性的问题

2.3、解决方法

  • 1.通过访问限定符号的方式对各个基类继承的同名成员进行赋值
访问限定符号方式:   基类 + :: + 同名成员

在这里插入图片描述
由此可得菱形继承对象模型为:
在这里插入图片描述

  • 2.通过菱形虚拟继承的方式(让最顶层基类成员在子类d对象中只储存一份
//virtual 虚拟继承标识符
class B {
public:
	
	int _b;
};
class C1 :virtual public B//C1虚拟继承自B
{
public:
	int c1;
};
class C2 :virtual public B//C2虚拟继承自B
{
public:
	int c2;
};
class D :public C1, public C2
{
public:
	int _d;
};
int  main()
{
	D d;
	d.c1 = 1;
	d.c2 = 2;
	d._b = 3;
	d._d = 5;
	return 0;
}

在这里插入图片描述
通过内存监视窗口,细心的铁铁可以发现d对象成员的_d加载到内存的最下面(但这其实也符合之间将的普通继承的对象模型);
注意啦在c1和c2成员的上面分别有一个地址,那么这个地址又是干什么用的呢???

  • 而这也便是虚拟继承的特性啦!!!

2.3.(1)虚拟继承

1. 对象模型
在这里插入图片描述

  • 上述图形,也展示了此刻的构造函数,没有,编译器则一定会提供默认构造函数,有,编译器也会对其进行修改(对其前四个字节进行赋值操作-----虚表指针)

2.实例展示
如上述实例的菱形虚拟继承代码:
在这里插入图片描述
从内存上查看这两个虚基表指针的内容
在这里插入图片描述
由此综上,可得实例代码的对象模型为:
在这里插入图片描述

注意:菱形虚拟继承主要用于解决菱形继承的二义性

总结

以上就是今天要讲的内容,本文主要讲了单继承,多继承以及菱形继承的概念,对象模型,以及其在VS2019上的展示。当然本文重点也当然是菱形虚拟继承啦~~~~
在这里插入图片描述

  • 最后感谢各位铁铁们的点击与观看
  • 当然若有不准确的地方,也希望请各位大佬加以指点,感谢~~~
  • 当然,铁铁给予的一份小小的关注,都将成为我不懈的动力!!!
    在这里插入图片描述
  • 8
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 7
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 7
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值