• 虚函数的地址存放于虚函数表中。运行期多态就是通过虚函数和虚函数表实现的。
    类的对象内部会有指向类内部的虚表地址的指针(每个类用了一个虚表,每个类的对象用了一个虚指针)。
    通过这个指针调用虚函数。虚函数的调用会被编译器转换为对虚函数表的访问。

  • ptr->f(); //ptr代表this指针,f是虚函数
    *(ptr->vptr[1])(ptr);
    ptr代表一个this指针,ptr指向的vptr是类内部的虚表指针。这个虚表指针会被放在类的最前方,
    1就是虚函数指针在虚函数表中的索引值。在这个索引值表示的虚表的槽中存放的就是f()的地址。

  • 虚表指针的名字也会被编译器更改,所以在多继承的情况下,类的内部可能存在多个虚表指针。通过不同的
    名字被编译器标识。

  • 虚函数表中可能还存在其他的内容,如用于RTTI的type_info类型。或者直接将虚基类的指针放在虚表中。
    压制多态可以通过域操作符进行

  • 单继承
    这种情况下,派生类中仅有一个虚函数表。这个虚函数表和基类的虚函数表不是一个表(无论派生类有没有
    重写基类的虚函数),但是如果派生类没有重写基类的虚函数的话,基类和派生类的虚函数表指向的函数地址都是
    相同的。

例子

class A
{public:A(int _a1 = 1) : a(_a1) { }virtual void f() { cout << "A1::f" << endl; }virtual void g() { cout << "A1::g" << endl; }~A() {}
private:int a;
};
class B : public A
{public:B(int _a1 = 1, int _c = 4) :A(_a1), b(_c) { }virtual void g() { cout << "C::g" << endl; }
private:int b;
};

*因为A有virtual void f(),和g(),所以编译器为A类准备了一个虚表vtableA,内容如下:
A::f的地址
A::g的地址
B因为继承了A,所以编译器也为B准备了一个虚表VtableB,内容如下:
A::f的地址
B::g的地址
因为B::g重写了,所以B的虚表的g放的是B::g的入口地址,但是f是从上面的A继承下来的,所以
f的地址是A::f的入口地址。
在构造B的对象的时候即(B b),编译器分配内存空间,除了classA的int a,B的成员int b;以外,还分配了一个虚指针vptr,
指向B的虚表vtableB,b的布局如下:
vptr:指向B的虚表vtableB
int a:继承A的成员
int b:B成员
A pa =&b;
pa的结构就是A的布局(就是说用pa只能访问到b对象的前两项,访问不到第三项int b)
pa->g()中,编译器知道的是,g是一个声明为virtual的成员函数,而且其入口地址放在表格的第2项,那么编译器
编译这条语句的时候就如是转换(pa->vptr)[1]。这一项放的是B::g()的入口地址,则就实现了多态

虚函数表和虚函数指针相关推荐

  1. C++虚函数表、虚函数指针(侯捷)

    C++虚函数表.虚函数指针(侯捷)

  2. 虚函数、虚函数表、虚继承

    1.虚函数 虚函数的定义: 虚函数必须是类的 非静态成员函数(且非构造函数),其访问权限是public(可以定义为privateor proteceted, 但是对于多态来说,没有意义),在基类的类定 ...

  3. C++类的虚函数表和虚函数在内存中的位置

    C++类的虚函数表和虚函数在内存中的位置 C++类的虚函数表和虚函数在内存中的位置 虚函数表和虚函数在内存中的位置说明 参考 C++类的虚函数表和虚函数在内存中的位置 虚函数表指针是虚函数表所在位置的 ...

  4. C++虚函数,虚函数表,虚继承,虚继承表

    一.虚函数 类中用virtual关键字修饰的函数. 作用:主要是实现了多态的机制.关于多态,简而言之就是用父类型别的指针指向其子类的实例,然后通过父类的指针调用实际子类的成员函数.这种技术可以让父类的 ...

  5. 虚函数表 以及 虚函数表的继承过程

    目录 一.虚函数表 和 虚表继承 1.虚函数表 2.虚表继承 (1) 子类未重写父类虚函数 (2) 子类重写了父类虚函数 二.虚表的特点 1.同一个类的对象的虚表指针相同 2.多继承时子类中的两个父类 ...

  6. C++虚函数表的底层原理 到底有几张虚函数表? 虚函数表是怎么维护的?

    昨天读了陈皓前辈博客中关于虚函数表底层原理的一篇博客,本着实践出真知的出发点,遂写了相应的测试代码去检验,发现最后测试出来的结果和陈皓博客中说明的情况存在出入.目前尚不清楚是不同编译器底层实现原理不同 ...

  7. Cpp 对象模型探索 / 虚函数表和虚函数表指针的创建时机

    一.虚函数表 在编译期间创建.编译器会为每个类确定好虚函数表(vtbl)的内容. 二.虚函数表指针 虚函数表指针跟随着对象,在运行期间创建.由于在编译期间编译器为每个类创建好了 vtbl,并且编译器会 ...

  8. 9-3:C++多态之多态的实现原理之虚函数表,虚函数表指针静态绑定和动态绑定

    文章目录 (1)虚函数表 (2)多态原理 (3)静态多态与动态多态 A:静态多态 B:动态多态 (1)虚函数表 如下代码,计算此带有虚函数的类的大小 #include <iostream> ...

  9. 虚函数,虚函数表,虚函数实现原理,虚函数实现机制,虚函数解决的问题

    虚函数 虚函数表 虚函数实现原理? 虚函数解决的问题?虚函数解决问题的实现机制? 虚函数模型的构建? 虚函数模型的应用?

  10. java 虚函数表_虚函数表(vtable/virtual table/virtual method table)

    本文只是拿 Java 代码做说明的例子,不代表Java的vtable是这样实现的 虚函数表,又称 virtual method table (VMT), virtual function table, ...

最新文章

  1. 千里之堤毁于蚁穴------重点项目不能交付之谜(一)泥淖中的验收测试
  2. Hadoop家族学习路线图
  3. Redis+Nginx+JVM+设计模式+Spring全家桶+Dubbo万字总结
  4. Intel Realsense D435 管道配置文件类(pipeline_profile)与流配置文件类(config)
  5. SL项目开发自定义控件封装之新建自定义控件类库
  6. SAP 电商云 Spartacus UI production build 时遇到和 orderCore 相关的错误
  7. 《数据科学R语言实践:面向计算推理与问题求解的案例研究法》一一2.5 为跨年度的个人参赛选手构造记录...
  8. 计算机程序备份,将应用程序快照备份到计算机
  9. 记一次线上cpu飙升100%的排查过程
  10. 不同于NLP,数据驱动、机器学习无法攻克NLU,原因有三
  11. Qt笔记-Linux程序打印带颜色的字符串
  12. python爬虫架构师之路_一位资深 架构师大牛给予Java技术提升的学习路线建议
  13. 触发日期spring3整合quartz实现任务调度功能
  14. 期货品种产业链图表_化工
  15. 【Linux】字符转换命令expand
  16. 计算机组成原理2套题,计算机组成原理试卷2套含答案(大学期末复习资料).doc...
  17. MATLAB显示图像变白问题
  18. 【大厂笔试心得,你还不知道笔试的思路吗?】-- ACM模式篇、笔试题型介绍以及相关准备
  19. ember controller内调用save修改model数据时出现null的解决方案
  20. 数字化时代的市场营销

热门文章

  1. 结构体里数组的初始化
  2. Kali 2020 DHCP获取动态ip和静态IP设置方法
  3. java 汉字转拼音_java汉字转拼音
  4. SPSS 数据清理-基础
  5. JavaScript学习笔记二 标识符-字符类型
  6. 什么是社会融资规模,M0、M1、M2?
  7. 面向对象的英文全称叫做Object Oriented
  8. 基于air720等air7xx的4G模块luat程序下载
  9. 深度学习(Deep Learning)综述及其延伸,入门必看!
  10. 详谈外部浏览器如何实现复制微信号一键唤起微信号加好友