C++类的多态
多态按字面的意思就是多种形态。当类之间存在层次结构,并且类之间是通过继承关联时,就可能会用到多态。
C++多态就是当调用成员函数时,会根据调用函数的对象的类型来执行不同的函数。
一、静态多态
我们以前说过的函数重载就是一个简单的静态多态,静态多态是编译器在编译期间完成的,编译器会根据实参类型来选择调用合适的函数,如果有合适的函数可以调用就调,没有的话就会发出警告或者报错。
示例(book236.cpp)
/*
* 程序名:book236.cpp,此程序用于演示C++类的静态多态。
* 作者:C语言技术网(www.freecplus.net) 日期:20190525
*/
#include <stdio.h>
#include <string.h>
class CGirl // 定义超女类
{
public:
char m_name[50]; // 姓名
int m_age; // 年龄
int m_height; // 身高,单位:厘米cm
char m_sc[30]; // 身材,火辣;普通;飞机场。
char m_yz[30]; // 颜值,漂亮;一般;歪瓜裂枣。
int Show() // 显示超女基本信息的成员函数体
{ printf("姓名:%s,年龄:%d,身高:%d,身材:%s,颜值:%s\n",m_name,m_age,m_height,m_sc,m_yz); }
};
class CKCon:public CGirl // 定义王妃类,从超女类继承
{
public:
char m_ch[50]; // 称号
char m_palace[50]; // 居住的宫殿
int m_sal; // 奉禄
int Show() // 显示王妃的称号、宫殿和奉禄
{ printf("姓名:%s,称号:%s,栖:%s,奉禄:%d两银子。\n",m_name,m_ch,m_palace,m_sal); }
};
int main()
{
CKCon KCon;
strcpy(KCon.m_name,"杨玉环"); KCon.m_age=28; KCon.m_height=168;
strcpy(KCon.m_sc,"火辣"); strcpy(KCon.m_yz,"漂亮"); strcpy(KCon.m_ch,"杨贵妃");
strcpy(KCon.m_palace,"华清宫"); KCon.m_sal=10000;
CGirl *pGirl; // 基类的指针
CKCon *pCon; // 派生类的指针
pGirl=pCon=&KCon; // 都指向派生类
pGirl->Show(); // 将调用的是基类的Show方法
pCon->Show(); // 将调用的是派生类的Show方法
}
运行效果
在book236.cpp的main函数中,创建的是CKCon对象,如果采用基类指针调用Show方法,变成了调用CGirl类的Show方法,而不是CKcon类的Show方法,因为pGirl是CGirl的指针,pGirl->Show方法在程序编译期间就已经设置好了。
二、动态多态
动态多态是在程序运行时根据基类的引用(指针)指向的对象来确定自己具体该调用哪一个类的虚函数。
让我们对程序稍作修改,在CGirl类中,Show方法的声明前放置关键字 virtual,如下所示:
virtual int Show() // 显示超女基本信息的成员函数体
其它的代码都不变,编译并运行,结果如下:
此时,编译器看的是指针的内容,而不是它的类型。这就是多态的一般使用方式。
三、虚函数
虚函数是在基类中使用关键字 virtual 声明的函数,在派生类中重新定义虚函数。
我们想要的是在程序中可以根据所调用的对象类型来选择调用的函数,这种操作被称为动态链接,或后期绑定。
四、纯虚函数
我们可以在基类中只声明虚函数,没有函数的定义,在派生类中去实现函数的定义,这个时候就会用到纯虚函数。
class CGirl // 定义超女类
{
public:
char m_name[50]; // 姓名
int m_age; // 年龄
int m_height; // 身高,单位:厘米cm
char m_sc[30]; // 身材,火辣;普通;飞机场。
char m_yz[30]; // 颜值,漂亮;一般;歪瓜裂枣。
virtual int Show()=0; // 申明一个纯虚函数。
};
virtual int Show()=0;;告诉编译器,函数只有声明,没有定义,是纯虚函数。
五、C++ 接口(抽象类)
接口描述了类的行为和功能,是标准和规范,而不需要完成类的功能实现。
C++接口是用抽象类来实现的,如果类中至少有一个函数被声明为纯虚函数,则这个类就是抽象类。
设计抽象类的目的,是为了给其他类提供一个可以继承的基类。抽象类不能用于实例化对象,它只能作为接口使用。如果试图实例化一个抽象类的对象,会导致编译错误。
如果一个基类的派生类需要实例化,则必须实现每个虚函数的定义,如果没有在派生类中纯虚函数的定义会导致编译错误。
可用于实例化对象的类被称为具体类。
六、应用经验
对初学者来说,类的多态、虚函数这些概念可能难以理解,因为您想不到它的应用场景,在实际开发中,这些知识的应用场景也比较少,在一些大型的项目开发中才可能用到,二十年来我只用过一次。
各位只要了解一下这些知识就可以了,掌握不了就算了。
七、版权声明
C语言技术网原创文章,转载请说明文章的来源、作者和原文的链接。
来源:C语言技术网(www.freecplus.net)
作者:码农有道
如果文章有错别字,或者内容有错误,或其他的建议和意见,请您留言指正,非常感谢!!!
C++类的多态的更多相关文章
- C# 类的多态、结构、接口、抽象、虚函数总结
多态: 类的多态是通过在子类(派生类)中重载基类的虚方法或成员函数来实现的. 可见,重载和虚函数的重写,并在调用时用父类装箱子类对象,是实现多态的一种重要的编程方式. 接口: 接口是一种用来定义程序的 ...
- Python类的多态的例子
1 # -*- coding: utf-8 -*- 2 # 类的多态 3 4 # 定义Person父类 5 class Person(object): 6 def __init__(self, nam ...
- 第二十九节:Java基础知识-类,多态,Object,数组和字符串
前言 Java基础知识-类,多态,Object,数组和字符串,回顾,继承,类的多态性,多态,向上转型和向下转型,Object,数组,多维数组,字符串,字符串比较. 回顾 类的定义格式: [类的修饰符] ...
- Python 类的多态的运用
#类的多态的运用 #汽车类 class Car(object): def move(self): print("move ...") #汽车商店类 class CarStore(o ...
- day21-5 类的多态与多态性
类的多态与多态性 多态 多态指的是一类事物有多种形态,如动物有多种形态:人.狗.猪 import abc class Animal(metaclass=abc.ABCMeta): # 同一类事物:动物 ...
- Java类的多态机制
Java中将一个方法调用同一个方法主体关联起来被称作绑定. 绑定分为前期绑定和后期绑定.前期绑定是在编译器决定的,而后期绑定是在程序运行时决定的.Java中除了static方法和final方法(pri ...
- .NET Core CSharp初级篇 1-6 类的多态与继承
.NET Core CSharp初级篇 1-6 本节内容为类的多态与继承 简介 终于讲到了面向对象三大特性中的两大特性--继承与多态.通过继承与多态,我们能很好的将类的拓展性发挥到了极致.在下面的内容 ...
- day18-Python运维开发基础(单继承 / 多继承 / 菱形继承、类的多态)
1. 单继承 / 多继承 / 菱形继承 # ### 继承 : 一个类除了自身所拥有的属性方法之外,还获取了另外一个类的成员属性和方法 """ 一个类可以继承另外一个类,那 ...
- C++练习案例1.计算机类(利用多态实现)
c++简单计算机类 简介 大家好,这里是天天like的博客,这是我发的第一篇随笔,用来记录我的学习日程,大家可以相互学习,多多交流,感谢 今天我要记录的随笔是在学习c++多态的知识点练习改进的一个案例 ...
随机推荐
- A 小石的签到题
题目链接:https://ac.nowcoder.com/acm/contest/949/A 思路: 这题明确的说了是个签到题,但是一直怀疑不是签到题,是唬我的,结果仔细想了想真是这么回事. 每个人必 ...
- [LC] 318. Maximum Product of Word Lengths
Given a string array words, find the maximum value of length(word[i]) * length(word[j]) where the tw ...
- highcharts series几种写法
一.数据列 数据列是一组数据集合,例如一条线,一组柱形等.图表中所有点的数据都来自数据列对象,数据列的基本构造是: series : [{ name : '', data : [] }] 提示:数据列 ...
- web中间件之nginx
web中间件之nginx https://www.jianshu.com/p/d8bd75c0fb1b 对nginx正向代理和反向代理理解特别好的一篇文章. 一.nginx nginx缺点,负载均 ...
- Nginx 原理和架构
Nginx 是一个免费的,开源的,高性能的 HTTP 服务器和反向代理,以及 IMAP / POP3 代理服务器.Nginx 以其高性能,稳定性,丰富的功能,简单的配置和低资源消耗而闻名Nginx 里 ...
- win7/win8下vmware/VirtualBox虚拟网卡显示未识别网络的解决
http://blog.csdn.net/zengxianying/article/details/44017227
- jsp页面jstl标签库失效问题
可能是版本低的问题,启用jstl即可解决(仅供参考) <%@ page isELIgnored="false"%>
- Flask从负到零的一周
新的一年,因为似乎要做很多的数据库,准备入坑Flask.开了一次讨论,我感觉自己燃起来了.于是,先买了一个号角状的水杯压压惊.目前通过一周的艰辛努力,终于做了一个小网站,支持数据库增删改查,算是从零到 ...
- 18岁,赚到了人生中的第一个10W!
大家好,我是九歌 今年我18岁,赚到了我人生中的第一个10W 截至2019年10月14日,我已经做了43天的公众号啦,粉丝也悄然增长到了1W8,感谢各位读者朋友给我的支持和鼓励. 相信大部分读者都是从 ...
- Android空包签名
空包签名 搜狗.优亿等Android市场,上传应用需要提供一个与要上传的应用相同签名的空包.这个空包是相应官方市场提供的,下载好之后需要使用命令行进行签名.具命令如下: 1 jarsigner -ve ...