我们知道C++里 virtual函数可以用来实现多态。继承类可以实现自己的功能来覆盖基类。比如下面这段代码

#include<iostream>
#include<string>
using namespace std;
class BaseA{
public:BaseA(string n):name(n){}string getName() const;virtual void showMyName() const;string name;
};class DerivedA:public BaseA{
public:DerivedA(string n):BaseA(n){}string getName() const;virtual void showMyName() const;
};string BaseA::getName() const
{cout<<"base static"<<endl;return name;
}void BaseA::showMyName() const
{cout<<"base:"<<name<<endl;
}string DerivedA::getName() const
{cout<<"derived static"<<endl;return name;
}void DerivedA::showMyName() const
{cout<<"derived:"<<name<<endl;
}int
main()
{DerivedA * derivedA = new DerivedA(string("abcd"));BaseA baseA = * derivedA; //会调用copy constructor函数
baseA.showMyName();baseA.getName();BaseA * pBaseA = derivedA;pBaseA->showMyName();pBaseA->getName();return 0;
}

这段代码的输出:

base:abcd
base static
derived:abcd
base static

我们来解读一下:

BaseA baseA = * derivedA;  这里其实是构造了一个BaseA类,也就是构造了一个基类,虽然是右值是继承类。但这里会调用BaseA的default copy assignment函数,构造一个BaseA的实例。derivedA会被截断。那么当然了
  baseA.showMyName();baseA.getName();这俩行会调用BaseA的函数。

我们再看一下下面这行
BaseA * pBaseA = derivedA;这里声明了一个BaseA的指针 然后把指针指向派生类 DerivedA的一个实例。
再看下面的代码pBaseA->showMyName();
pBaseA->getName();showMyName我们定义成了Virtual,也就是在内存里会有个函数指针,指向不同的实现。对于derivedA来说,这个函数的指针当然是指向DerivedA的showMyName。而pBaseA拿到的是derivedA的指针,那么当然调用的函数也会是DerivedA的实现函数。这个就是所谓的动态绑定。

下面再看getName,相对于动态绑定函数,这是个静态函数,什么事静态函数呢,就是这个函数会根据对象的静态类型来调用。比如pBaseA的静态类型是BaseA,那么pBaseA所调用的就是BaseA的getName。
 

转载于:https://www.cnblogs.com/hojor/p/4424483.html

浅谈C++的virtual 动态绑定。相关推荐

  1. 浅谈c++静态绑定、动态绑定

    多态:指同一个实体同时具有多种形式,即一个名字可以具有多种语义.函数重载.类模板.函数模板等都属于多态性.通俗来说就是接口的多种不同实现方式. 函数绑定:就是函数的入口地址同函数调用相联系的过程. 分 ...

  2. 浅谈C#中virtual和abstract的区别

    virtual和abstract都是用来修饰父类的,通过覆盖父类的定义,让子类重新定义. 它们有一个共同点:如果用来修饰方法,前面必须添加public,要不然就会出现编译错误:虚拟方法或抽象方法是不能 ...

  3. 浅谈C#中的延“.NET研究”迟加载(2)——善用virtual

    之前的文章"浅谈C#中的延迟加载(1)--善用委托"中介绍了三层结构中在Model层对实体类的属性实现延迟加载的方法,该方法利用C#中的委托来实现,最后虽然延迟加载的目的得以实现, ...

  4. java中virtual关键字_浅谈virtual、abstract方法和静态方法、静态变量理解

    说点对这几个容易混淆的词的理解: 1.c++中的virtual方法的 virtual关键字主要是防止继承中重复继承父类的同一个方法而设置的标识. 2.virtual与abstract关键字的不同之处在 ...

  5. 浅谈 CRTP:奇异递归模板模式

    浅谈 CRTP:奇异递归模板模式 前言 建议先看一遍文末的参考资料! 建议先看一遍文末的参考资料! 建议先看一遍文末的参考资料! 思维导图 一.CRTP 是什么 CRTP 全称 : Curiously ...

  6. 浅谈c++中继承体系中易错点

    浅谈c++中继承体系中易错点 目前,就我工作经验来看,在c++中继承体系中总爱搞错的有两点: 不把基类中需要覆盖的方法为设置为虚方法. 不把基类中的析构函数设置为虚方法. 就第一点而言,如果基类中需要 ...

  7. 浅谈WPF的VisualBrush

    原文:浅谈WPF的VisualBrush 首先看看VisualBrush的解释,msdn上面的解释是使用 Visual 绘制区域,那么我们再来看看什么是Visual呢?官方的解释是:获取或设置画笔的内 ...

  8. JDK与JRE的关系和path的作用浅谈

    JDK与JRE的关系和path的作用浅谈 摘要:JDK与JRE的关系以及path的配置对于初学者是要明白的问题,那么具体的JDK与JRE的关系是什么呢?那么本文讲给你简单介绍. 标签:JDK与JRE关 ...

  9. 浅谈ASP.NET的Postback

    说道ASP.NET的Postback,就得说Web Page的生命周期,但是Web Page的生命周期却不是三言两语就能够说得清楚的,所以在这里单纯站的编程的角度,撇开Web Page 的生命周期浅谈 ...

最新文章

  1. linux的网络命令整理 更新中
  2. 新兴机器学习算法:在线学习
  3. 机器学习-机器学习概论(入门机器学习基础知识)
  4. LeetCode 409. 最长回文串(计数)
  5. 长假大考充电桩:堵车不可怕,没电才尴尬
  6. oracle数据库从AIX环境expdp迁移到linux环境(sec_case_sensitive_logon=true导致连接报错ORA-01017)
  7. LOJ#3085. 「GXOI / GZOI2019」特技飞行(KDtree+坐标系变换)
  8. 动态添加和删除 ListView 项
  9. ARM开发7.3.4 基础实训( 4 ) 矩阵式键盘的输入系统设计--LPC21XX
  10. SQL 分页查询显示
  11. BUUCTF WEB 第四页WP(持续更新)
  12. linux两台服务器文件实时同步
  13. oracle 存档终点修改,修改归档模式的存档终点 archive log list
  14. C语言编程:如何计算二叉树叶子结点数目?
  15. candence测量尺寸
  16. VuePress开启评论、VuePress评论功能。
  17. 长沙县:红红火火过大年 文化惠民暖人心
  18. PHP AES加密解密
  19. Bootstrap Method
  20. Linux之jkd、tomcat、mysql安装

热门文章

  1. Serverless Kubernetes:理想,现实与未来
  2. 课时 23:Kubernetes API 编程范式(陈显鹭)
  3. Dubbo 3.0 前瞻:重塑 Spring Cloud 服务治理
  4. python关键字as_python 之 import、from、as 关键字的 白话 解释与例子
  5. mysql 连接校对_教你轻松的掌握 MYSQL连接字符集和校对
  6. 无连接可靠传输_尽力传输是什么 尽力传输原理介绍【图文】
  7. 专门入侵检测linux叫什么,入侵检测系统分析及其在Linux下的实现(上)
  8. 服务器高并发时请求报错_基于redis的分布式锁防止高并发重复请求
  9. 笔记本电脑排行_笔记本电脑性价比排行2020
  10. 常见计算机英语词汇翻译,常见计算机英语词汇解释(1)