【C++】解决菱形继承而产生的虚基表(偏移量表)

news2024/11/25 1:51:53

文章目录

  • 继承概念
  • 切片和重定义
  • 派生类的默认成员函数
  • 菱形虚拟继承

继承概念

  继承(inheritance)机制是面向对象程序设计使代码可以复用的最重要的手段,它允许程序员在保持原有类特性的基础上进行扩展,增加功能,这样产生新的类,称派生类。继承呈现了面向对象程序设计的层次结构,体现了由简单到复杂的认知过程。以前我们接触的复用都是函数复用,继承是类设计层次的复用

=

  基类private成员在派生类中无论以什么方式继承都是不可见的。这里的不可见是指基类的私有成员还是被继承到了派生类对象中,但是语法上限制派生类对象不管在类里面还是类外面都不能去访问它。关键字class时默认的继承方式是private,使用struct时默认的继承方式是public

切片和重定义

  派生类对象 可以赋值给 基类的对象 / 基类的指针 / 基类的引用。这里有个形象的说法叫切片或者切割。寓意把派生类中父类那部分切来赋值过去。而基类对象不能赋值给派生类对象,因为子类继承父类后,可能会出现父类没有的成员变量,比如下面的 _No

  在继承体系中基类和派生类都有独立的作用域,子类和父类中有同名成员,若不指明类域,局部优先,会先调用子类函数。子类成员将屏蔽父类对同名成员的直接访问,这种情况叫隐藏,也叫重定义

派生类的默认成员函数

  这六个默认成员函数主要遵守以下规则,先用初始化列表初始化基类的那一部分,在初始化子类自己这一部分。先析构派生类在析构父类,若先析构父类,而子类可能还调用了父类的内容,就会出现野指针等等问题。记住构造先父后子,析构先子后父就行
  友元关系不能继承,也就是说基类友元不能访问子类私有和保护成员。
  基类定义了static静态成员,则整个继承体系里面只有一个这样的成员。无论派生出多少个子类,都只有一个static成员实例

菱形虚拟继承

  菱形继承:菱形继承是多继承的一种特殊情况。菱形继承的问题:菱形继承有数据冗余和二义性的问题。在 Assistant 的对象中 Person 成员会有两份,从 Studentteacher 对象中各继承了一份,Assistant 对象若使用了 Person 成员,就会报错,指代不明确,除非指明是 Student 或者 teacher 的类域

菱形继承

class A
{
public:
	int _a;
};
class B :  public A
{
public:
	int _b;
};
class C :  public A
{
public:
	int _c;
};
class D : public B, public C
{
public:
	int _d;
};

int main()
{
	D d;
	d.B::_a = 1;
	d.C::_a = 1;
	d._b = 3;
	d._c = 4;
	d._d = 5;
	return 0;
}

对于以上带代码,先看菱形继承的对象模型:因为 B,C 都有 _a, 如果 d._a 这样直接访问就会报错,不确定你访问的是B对象还是C对象中的_a

菱形虚拟继承

class A
{
public:
	int _a;
};
class B : virtual public A
{
public:
	int _b;
};
class C : virtual public A
{
public:
	int _c;
};
class D : public B, public C
{
public:
	int _d;
};

int main()
{
	D d;
	d.B::_a = 1;
	d.C::_a = 2;
	d._b = 3;
	d._c = 4;
	d._d = 5;
	d._a = 0;
	return 0;
}

对于以上带代码,先看菱形虚拟继承的对象模型:



偏移量表内容



  这里可以分析出D对象中将A放到的了对象组成的最下面,这个A同时属于B和C。那么B和C如何去找到公共的A呢?这里是通过了B和C的两个指针,指向的一张表。这两个指针叫虚基表指针,这两个表叫虚基表。虚基表中存的偏移量。通过偏移量可以找到下面的A

思考一:为什么要建偏移量表,而不直接存偏移量?
  因为 A 类对象可能不止一个成员变量,如果多于一个的话,D 里面 B 和 C对象都要存多个偏移量,肯定没有直接放一个偏移量表地址合适,这样极大的减小了 D 对象的大小

思考二:为什么偏移量表里面不直接存 _a 的地址,而是存一个偏移量?
  因为如果你表里存 _a 地址的话, D 实例化出的d1和d2 中的 _a 地址是不一样的,但它们相对B和C对象的偏移量却是相同的。因此存偏移量的话可以保证所有 D 实例化出的 d1, d2, d3等等对象,都公用同一张表

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/794865.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

LeetCode91.Decode-Ways<解码方法>

题目&#xff1a; 思路&#xff1a; 关键在于有没有0,其次能不能二位.二位的要求是在 1-- 26的范围内.所以动态规划的时候需要限制. 代码是&#xff1a; //codeclass Solution { public:int numDecodings(string s) {int n s.size();vector<int> dp(n1, 0); // 定义状…

java使用htmlunit + jsoup 爬网站图片案例(爬虫学习)

申明 该文章用于自己学习爬虫使用 案例分析 目的: 从百度图片中搜索"风景"并下载图片到本地 思路: 使用htmlunit进行模拟用户操作, 并使用jsoup对数据进行解析,获取到需要的数据后,再下载到本地保存 htmlunit官网 jsoup官网 操作步骤 使用谷歌浏览器打开百度图片…

用html+javascript打造公文一键排版系统8:附件及标题排版

最近工作有点忙&#xff0c;所 以没能及时完善公文一键排版系统&#xff0c;现在只好熬夜更新一下。 有时公文有包括附件&#xff0c;招照公文排版规范&#xff1a; 附件应当另面编排&#xff0c;并在版记之前&#xff0c;与公文正文一起装订。“附件”二字及附件顺序号用3号黑…

Mysql适用于初学者的前期入门资料

文章目录 前言一、SQL语句分类二、SQL语句的书写规范三.数据库操作四、MySQL字符集1、问题① 五、UTF8和UTF8MB4的区别六、数据库对象七、数据类型八、表的基本创建1、创建表2、查看表3、删除表4、修改表结构5、复制表的结构 九、数据库字典十、表的约束1、非空约束(NOT NULL)2…

matplotlib从起点出发(4)_Tutorial_4_Lifecycle

1 一幅图像的生命周期 本教程旨在揭示使用matplotlib绘制的一幅图像的生命周期&#xff0c;包括它的开始、中间和结束。我们将从一些原始数据开始&#xff0c;最后保存自定义可视化的图形。在此过程中&#xff0c;我们尝试使用matplotlib突出一些简洁的功能和最佳实践。 2 关…

【Matlab】基于粒子群优化算法优化BP神经网络的时间序列预测(Excel可直接替换数据)

【Matlab】基于粒子群优化算法优化BP神经网络的时间序列预测&#xff08;Excel可直接替换数据&#xff09; 1.模型原理2.数学公式3.文件结构4.Excel数据5.分块代码5.1 fun.m5.2 main.m 6.完整代码6.1 fun.m6.2 main.m 7.运行结果 1.模型原理 基于粒子群优化算法&#xff08;Pa…

【LeetCode 75】第九题(443)压缩字符串

目录 题目: 示例: 分析: 题目: 示例: 分析: 给一个字符串,如果该字符有连续的相同的字符,则只保留一个字符,并在该字符后加上该字符连续的数量.例如原数组为 [a,a,a],则因为字符a连续了三次,因此可以压缩为[a,3],我们需要注意的是数字也需要是字符,则如果字符连续次数不止有…

SpringCloud学习路线(13)——分布式搜索ElasticSeach集群

前言 单机ES做数据存储&#xff0c;必然面临两个问题&#xff1a;海量数据的存储&#xff0c;单点故障。 如何解决这两个问题&#xff1f; 海量数据的存储问题&#xff1a; 将索引库从逻辑上拆分为N个分片&#xff08;shard&#xff09;&#xff0c;存储到多个节点。单点故障…

C++笔记之memset分析

C笔记之memset分析 code review! 文章目录 C\笔记之memset分析1.介绍2.误区总结3.代码一&#xff0c;char数组和uint8_t使用memset4.代码三&#xff0c;int数组使用memset 1.介绍 2.误区总结 参考文章&#xff1a;Cmemset踩坑 3.代码一&#xff0c;char数组和uint8_t使用mem…

2023年河北省研究生数学建模竞赛D题中国钢铁工业低碳转型与高质量发展路径优化研究思路和代码

D题中国钢铁工业低碳转型与高质量发展路径优化研究 目前已写出D题初步代码&#xff0c;下载地址&#xff1a;【2023年河北省研究生数学建模竞赛D题初步思路和代码-哔哩哔哩】 https://b23.tv/g2ATbX5 随着我国工业化、城镇化进程的加快和消费结构持续升级&#xff0c;能源需求…

tty(五)串口的打开过程

一、字符设备完成注册 我们知道&#xff0c;在serial核心层提供了2个重要接口 uart_register_driver uart_add_one_port 上者通过调用tty核心的接口&#xff0c;完成了tty_driver的动态分配和注册&#xff0c;然而此时并没有看到创建字符设备&#xff0c; 通过对uart_add_one…

货拉拉基于 Flink 计算引擎的应用与优化实践

摘要&#xff1a;本文整理自货拉拉实时研发平台负责人王世涛&#xff0c;在Flink Forward Asia 2022 平台建设专场的分享。本篇内容主要分为六个部分&#xff1a; Flink 在货拉拉的使用现状Flink 平台化性能优化主题数据准确性主题稳定性主题未来展望 点击查看原文视频 & 演…

【leetcode】链表的中间节点|链表中倒数第k个节点

目录 1.链表的中间节点 2.链表中倒数第k个节点 1.链表的中间节点 思路1&#xff1a;遍历链表&#xff0c;统计节点个数count&#xff0c;返回第count/2 1个节点 &#x1f4d6;Note:注意循环条件为--mid&#xff0c;--mid循环执行mid-1次&#xff0c;mid--循环mid次&#xf…

SpringBoot 8种异步实现方式

前言&#xff1a;异步执行对于开发者来说并不陌生&#xff0c;在实际的开发过程中&#xff0c;很多场景多会使用到异步&#xff0c;相比同步执行&#xff0c;异步可以大大缩短请求链路耗时时间&#xff0c;比如&#xff1a;「发送短信、邮件、异步更新等」&#xff0c;这些都是…

采用串级控制和超高精度PID调节器的微张力精密控制技术

摘要&#xff1a;采用当前的各种涂布机很难适用气体扩散层这类脆性材料的涂布工艺&#xff0c;需要控制精度更高的微张力控制系统。为此本文基于串级控制原理&#xff0c;提出了采用双闭环PID控制模式和超高精度PID张力控制器的解决方案&#xff0c;一方面形成浮动摆棍闭环和主…

python机器学习(五)逻辑回归、决策边界、代价函数、梯度下降法实现线性和非线性逻辑回归

线性回归所解决的问题是把数据集的特征传入到模型中&#xff0c;预测一个值使得误差最小&#xff0c;预测值无限接近于真实值。比如把房子的其他特征传入到模型中&#xff0c;预测出房价&#xff0c; 房价是一系列连续的数值&#xff0c;线性回归解决的是有监督的学习。有很多场…

kafka权威指南学习以及kafka生产配置

0、kafka常用命令 Kafka是一个分布式流处理平台&#xff0c;它具有高度可扩展性和容错性。以下是Kafka最新版本中常用的一些命令&#xff1a; 创建一个主题&#xff08;topic&#xff09;&#xff1a; bin/kafka-topics.sh --create --topic my-topic --partitions 3 --replic…

【论文阅读22】Label prompt for multi-label text classification

论文相关 论文标题&#xff1a;Label prompt for multi-label text classification&#xff08;基于提示学习的多标签文本分类&#xff09; 发表时间&#xff1a;2023 领域&#xff1a;多标签文本分类 发表期刊&#xff1a;Applied Intelligence&#xff08;SCI二区&#xff0…

生态系统景观指数-聚集度指数AI计算

景观指数是景观生态学的常见指标&#xff0c;可用于不同生态系统的特征识别。景观指数是反映景观结构与空间格局的定量指标&#xff0c;目前已成为景观生态学领域常用的分析景观格局、度量空间异质性的重要方法。不同水平下的指数结果往往代表不同含义&#xff0c;应在把握指数…

git冲突“accept theirs”和“accept yours”

Accept Yours 就是直接选取本地的代码&#xff0c;覆盖掉远程仓库的 Accept Theirs 是直接选取远程仓库的&#xff0c;覆盖掉自己本地的 我们选择Merge,自己手动行进选择、修改。 这里左边部分是你本地仓库的代码&#xff0c;右边部分是远程仓库的代码&#xff0c;中间的res…