C/C++中多态性与虚函数
2015-12-16 12:21
302 查看
需要的先验知识:多态性的概念、在类继承中是否定义虚函数的例子
基类指针本来是用来指向基类对象的,当他用来指向派生类对象时。则会发生指针转换,将派生类对象的指针转换为基类对象的指针,所以此时基类指针指向的是派生类对象中基类的部分(故此时指针不能访问派生类特有的部分)。
重载与虚函数的差别:重载的“多态性”是发生在编译时的,根据调用函数的参数个数与参数类型决定到底调用重名函数的哪一个。而虚函数的多态性是发生在运行时的,根据调用函数的对象类型而选择调用哪一个重名函数。
基类中声明为虚函数的功能,其在派生类中的同名函数默认为虚函数(可省略virtual 定义)。此时将所有的虚函数都放在了一个虚函数表中,而留了一个指针P在类中。基类指针(指向派生类)调用函数时,通过指针P指向对象的类型(即偏移量)来找到所要的虚函数表中的虚函数。从而实现了多态性。
而sizeof(各类)的结果为:
说明:
1)一个类中若有虚函数,(不论是自己的虚函数,还是继承而来的),那么类中就有一个成员变量:虚函数指针,这个指针指向一个虚函数表,虚函数表的第一项是类的typeinfo信息,之后的项为此类的所有虚函数的地址。
2)假设经过成员对齐后的类的大小为size个字节。那么类的sizeof大小可以这么计算:size + 4*(虚函数指针的个数n)。代码中,DerivedFromTwo继承自2个分支,所以有2个虚函数指针,所以sizeof大小为0 + 4* 2 = 8。
3)带有虚函数的类的sizeof大小,实际上和虚函数的个数不相关,相关的是虚函数指针。
基类指针本来是用来指向基类对象的,当他用来指向派生类对象时。则会发生指针转换,将派生类对象的指针转换为基类对象的指针,所以此时基类指针指向的是派生类对象中基类的部分(故此时指针不能访问派生类特有的部分)。
重载与虚函数的差别:重载的“多态性”是发生在编译时的,根据调用函数的参数个数与参数类型决定到底调用重名函数的哪一个。而虚函数的多态性是发生在运行时的,根据调用函数的对象类型而选择调用哪一个重名函数。
基类中声明为虚函数的功能,其在派生类中的同名函数默认为虚函数(可省略virtual 定义)。此时将所有的虚函数都放在了一个虚函数表中,而留了一个指针P在类中。基类指针(指向派生类)调用函数时,通过指针P指向对象的类型(即偏移量)来找到所要的虚函数表中的虚函数。从而实现了多态性。
含有虚函数的类sizeof大小
<span style="font-size:18px;">class Base_A{ pubulic: virtual void funA(); virtual void funA2(); }; class Base_B{ pubulic: virtual void funB(); }; class C_1:pubulic A{ pubulic: virtual void funB(); }; class C_2:pubulic Base_A,pubulic Base_B{ pubulic: virtual void funA(); virtual void funAA(); virtual void funB(); };</span>
而sizeof(各类)的结果为:
<span style="font-size:18px;">Base_A</span> | <span style="font-size:18px;"><span style="font-size:18px;"></span></span><pre name="code" class="cpp"><span style="font-size:18px;"></span><pre name="code" class="cpp"><span style="font-size:18px;">Base_B</span> | <span style="font-size:18px;">C_1</span> | <span style="font-size:18px;">C_2</span> |
4 | 4 | 4 | 8 |
1)一个类中若有虚函数,(不论是自己的虚函数,还是继承而来的),那么类中就有一个成员变量:虚函数指针,这个指针指向一个虚函数表,虚函数表的第一项是类的typeinfo信息,之后的项为此类的所有虚函数的地址。
2)假设经过成员对齐后的类的大小为size个字节。那么类的sizeof大小可以这么计算:size + 4*(虚函数指针的个数n)。代码中,DerivedFromTwo继承自2个分支,所以有2个虚函数指针,所以sizeof大小为0 + 4* 2 = 8。
3)带有虚函数的类的sizeof大小,实际上和虚函数的个数不相关,相关的是虚函数指针。
相关文章推荐
- c语言字符串 数字转换函数大全
- C++11.0 新特性
- C++ AVFrame转BMP 或者其他形式转化也可
- 冒泡算法
- C++ Vector
- c语言数据类型及表示 l
- C++ Map
- C++系列: 如何将十六机制的字符串转成整数
- c语言中内存管理
- 23种设计模式C++实例之享元模式
- PY++ 自动将你的C++程序接口封装供python调用
- c++: allocator, uninitialized_copy, uninitialized_fill_n
- 23种设计模式C++实例之组合模式
- 23种设计模式C++实例之桥接模式
- 开发中遇到C++ 问题,记在这里,方便以后查看
- 23种设计模式C++实例之装饰模式
- 23种设计模式C++实例之代理模式
- c语言基础
- oc中new和init的区别
- 23种设计模式C++实例之适配器模式