C++类与对象笔记十四:多态三:动态多态的好处

动态多态的好处

案例描述:

分别利用普通写法和多态技术:设计实现两个操作数进行运算的计算器类

多态的有点:

  • 代码组织结构清晰
  • 可读性强
  • 利于前期和后期的扩展以及维护

先来看一下普通实现写法: 

#include<iostream>
using namespace std;

// 多态带来的好处:
// 分别利用普通写法和多态技术实现计算器。
class Calculator
{
public:

	int getResult(string oper)
	{
		if (oper=="+")
		{
			return m_Num1 + m_Num2;
		}
		else if (oper=="-")
		{
			return m_Num1 - m_Num2;
		}
		else if (oper=="*")
		{
			return m_Num1 * m_Num2;
		}
		// else
		// 如果想扩展新的功能,比如:平方,立方,开方等,需要修改源码。
		// 在真实开发中 提倡 开闭 原则。
		// 开闭原则:对扩展进行开放,对修改进行关闭。
		// 因为修改的话:要整体大段代码查询,如果要扩展,只要继承重载就可以。
		// 如果用多态,就方便多了。
	}

	int m_Num1;
	int m_Num2;
};

void test01()
{
	Calculator cal;
	cal.m_Num1 = 10;
	cal.m_Num2 = 20;

	cout << cal.m_Num1 << " + " << cal.m_Num2 << " = " << cal.getResult("+") << endl;
	cout << cal.m_Num1 << " - " << cal.m_Num2 << " = " << cal.getResult("-") << endl;
	cout << cal.m_Num1 << " * " << cal.m_Num2 << " = " << cal.getResult("*") << endl;

}

int main()
{

	test01();
	system("pause");
	return 0;
}

在计算器类Calculator中getResult方法将类中两个成员相加。方法中有个string类型参数,输入不同的string符号,来实现多态控制。

但是这样有个问题:如果后续需要增加其他运算,比如平方,就需要修改源码,并且,修改完之后,要检查整体代码有没有问题。如此做法有违编程的开闭原则

开闭原则:对扩展进行开放,对修改进行关闭。

《C#学习笔记(二十二)抽象类与开闭原则:抽象类和接口怎么来的?》一文中:我们提到:

 我们应该封装一些固定,不变的,稳定的、确定的成员;把不确定的,有可能改变的成员抽象为抽象成员、抽象类,留给子类去实现。

抽象类和开闭原则天生就是一对。




利用多态实现计算器

先声明一个抽象类AbstractCalculator类中什么功能都不写。声明两个成员属性待用。把getResult函数抽象出来,写为虚函数,因为不知道后面具体如何实现,所以函数内部,只要写一个return 0即可。类似于C#中的接口类或者抽象类。

class AbstractCalculator
{
public:
	virtual int getResult()
	{
		return 0;
	}
	int m_Num1;
	int m_Num2;
};

然后,写一个加法/减法/乘法计算器的类。继承于抽象类AbstractCalculator。其中重写虚函数virtual可带可不带。

// 加法计算器类。
class AddCalculator :public AbstractCalculator
{
public:
	int getResult()
	{
		return m_Num1 + m_Num2;
	}
};

// 减法计算器类
class SubCalculator :public AbstractCalculator
{
public:
	int getResult()
	{
		return m_Num1 - m_Num2;
	}
};
class MultiCalculator :public AbstractCalculator
{
public:
	int getResult()
	{
		return m_Num1 * m_Num2;
	}
};

调用执行情况:

void test01()
{
	// 多态的使用条件:
	// 父类的指针或者引用,指向子类的对象。Animal animal = cat;
	// 我们写一下:父类的指针指向子类对象。
	AbstractCalculator* abc = new AddCalculator;   // 发生多态。
	abc->m_Num1 = 20;
	abc->m_Num2 = 30;
	cout << abc->m_Num1 << " + " << abc->m_Num2 << " = " << abc->getResult() << endl;
	
	// 因为这个对象是new出来的,存在堆区,手动开辟创建,手动释放。
	delete abc;

	abc = new SubCalculator;
	abc->m_Num1 = 30;
	abc->m_Num2 = 20;
	cout << abc->m_Num1 << " - " << abc->m_Num2 << " = " << abc->getResult() << endl;
	delete abc;

	abc = new MultiCalculator;
	abc->m_Num1 = 30;
	abc->m_Num2 = 20;
	cout << abc->m_Num1 << " * " << abc->m_Num2 << " = " << abc->getResult() << endl;
	delete abc;
}

代码量变大了。

多态带来的好处:

  1. 组织结构清晰。如果有一天发现:某个运算错了,比如加法。比如减法,马上可以定位到。而且只要修改这个类就行了,大型项目,列的越清晰越好。降低强耦合。
  2. 可读性强。一眼能看懂别人写的代码:并非你比别人强,而是写代码这个人厉害,让你一眼看懂。他也可以写成你看不懂的样子:那种样子叫做:恶心。
  3. 对于前期和后期的扩展以及维护性高。

增加新功能:是追加代码,而不是修改原来的代码。



这个案例是根据输入的运算符来操作运算。

C#中的多态案例实现:

C#学习笔记(二十一)之实现多态的手段

C#中使用object作为参数来控制实现类型多态的。可以根据输入的两个对象类型,来选择不同运算。

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
多态好处 1,能使继承基类的子类重写(覆盖)基类定义的相同函数名字和参数的虚函数接口,使子类对象更符合自己的要求或特征 一个简单粗暴的比喻就是 假设人是基类,派生出了子类男人和女人. 则子类男人和女人拥有基类人的相同特征或行为---如会吃饭,要睡觉.... 但男人类和女人类也有不同的地方---如男的有jj,女的没有. 解决这个问题就是在基类人定义一个虚函数接口,具体怎么定义,由继承的子类去自己定义,通过自定义,子类有了符合自己的特征 2,转自网上的一个比喻 将父类比喻为电脑的外设接口,子类比喻为外设,现在我有移动硬盘、U盘以及MP3,它们3个都是可以作为存储但是也各不相同。如果我在写驱动的时候,我用个父类表示外设接口,然后在子类中重写父类那个读取设备的虚函数,那这样电脑的外设接口只需要一个。但如果我不是这样做,而是用每个子类表示一个外设接口,那么我的电脑就必须有3个接口分别来读取移动硬盘、U盘以及MP3。若以后我还有SD卡读卡器,那我岂不是要将电脑拆了,焊个SD卡读卡器的接口上去? 所以,用父类的指针指向子类,是为了面向接口编程。大家都遵循这个接口,弄成一样的,到哪里都可以用。 3,提高程序的可复用性,提高可扩充行和可维护性,一个接口,多种实现,各自不同. 动态多态的基础知识: 首先百度自己去弄懂什么是静态多态?什么是动态多态 易语言的类方法全部是强制成虚函数的 具体参考易语言目录下的例子 e\samples\基本例程\面向对象编程.e 易语言面对对象编程  类的创建与使用 help.plgzs.com/zlsc/oop.htm 但易语言对类的封装并不完美,与标准的c++的类很多功能没有 易语言是c++写的,所以要在在这之前必须要弄懂c++中什么是重写,重载,隐藏,3个不同的概念,不懂就百度,另外别拿C#和java的对比c++的重写 1.重写必须继承,重载不用。 2.重写的方法名,参数数目相同,参数类型兼容,重载的方法名相同,参数列表不同。 3.重写的方法修饰符大于等于父类的方法,重载和修饰符无关。 4.重写不可以抛出父类没有抛出的一般异常,可以抛出运行时异常 特点: 1. 指不同作用域中(派生类和基类)同名函数的定义 2. 函数名、参数均完全相同 3. 基类对应方法前有 virtual,即被声明为虚函数 作用: 基类指针和引用在调用对应方法时,根据所指对象类型实现动态绑定。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值