一、虚函数1.虚函数表位置分析 类:有虚函数,这个类会产生一个虚函数表 类的对象:有一个指针(vptr)会指向类的虚函数表——虚函数表指针。(位置可能在类内存空间的开头,也可能在末尾,具体由编译器实现...

一、虚函数
1.虚函数表位置分析
类:有虚函数,这个类会产生一个虚函数表
类的对象:有一个指针(vptr)会指向类的虚函数表——虚函数表指针。(位置可能在类内存空间的开头,也可能在末尾,具体由编译器实现决定)
2.继承关系作用下虚函数的手工调用
拿到虚函数表的地址,通过定义函数指针并赋值的方式可以直接调用虚函数。子类的虚函数会覆盖父类的虚函数。
3.虚函数表分析
(1)一个类只有包含虚函数才会存在虚函数表,同属于一个类的对象共享虚函数表,但拥有各自的虚函数表指针(vptr)。当然所有的该类对象的vptr都指向同一个虚函数表。
(2)父类中有虚函数就等于子类中有虚函数。(父类中有虚函数表则子类中肯定有虚函数表) 因为子类会继承父类。
如果子类中将父类虚函数的virtual去掉,函数就不再是虚函数?
在父类中是虚函数,即使子类中该函数不写virtual,它依然是虚函数。
不管是父类还是子类,每一个类都只有属于自己的唯一虚函数表。子类中是否会存在多个虚函数表?
(3)如果子类中完全没有新的虚函数,则子类虚函数表的内容与父类虚函数表的内容相同。但两个虚函数表在内存中的位置是不同的。是两个虚函数表。虚函数表中的每一项包含一个虚函数的首地址,但如果子类的虚函数表某项和父类虚函数表某项代表同一个函数(这表示子类没有覆盖父类的虚函数)则该表项所指向的函数相同。
(4)超出虚函数表部分内容不可知。
(5)当子类对象为父类对象赋值时,子类中的属于父类的那一部分会被编译器自动区分(切割)出来并拷贝给父类对象;所以BaseClass base = derive;实际做了两件事:一、生成了一个base对象;二、用derive的部分值来对base对象进行了初始化。 (但此时编译器在处理base对象的虚函数表指针 值的时候,编译器会根据base的类型来自动决策为BaseClass 的虚函数表地址)
(4)OO(面向对象)和OB(基于对象)概念
C++是通过类的指针和引用来支持多态,这是一种程序设计风格,这就是我们常说的面向对象。object-oriented model
OB(object-base)也叫ADT抽象数据模型[abstract datatype model],不支持多态,执行速度更快。因为函数调用的解析不需要运行时决定(没有多态),比如Base *pbase = new Derive();Base &base2 = derive2;而是在编译期间完成,内存空间紧凑程度上更为紧凑,因为没有虚函数这些概念。
但OB(object-base)的设计灵活性上较差,C++既支持面向对象程序设计。也支持基于对象程序设计。
3.多重继承虚函数表分析
沃梦达教程
本文标题为:c++ 之 内存模型:虚函数篇


猜你喜欢
- Qt计时器使用方法详解 2023-05-30
- C++ 数据结构超详细讲解顺序表 2023-03-25
- C语言手把手带你掌握带头双向循环链表 2023-04-03
- 详解C语言中sizeof如何在自定义函数中正常工作 2023-04-09
- ubuntu下C/C++获取剩余内存 2023-09-18
- C语言详解float类型在内存中的存储方式 2023-03-27
- Easyx实现扫雷游戏 2023-02-06
- c++ const 成员函数,返回一个 const 指针.但是返回的指针是什么类型的 const? 2022-10-11
- 我应该为我的项目使用相对包含路径,还是将包含目录放在包含路径上? 2022-10-30
- C语言qsort()函数的使用方法详解 2023-04-26