策略模式:某些对象使用的算法可能多种多样,经常改变,如果将这些算法编码到代码中,会使代码变得异常负责,而且有时候支持不使用的算法可能是一种性能负担。
对于上面描述可以举如下的列子解释。比如如下代码所示:
#pragma once
#include<iostream>
using namespace std;
//假如我们要实现一个功能:输入某个国家可以相应计算出该国家的税金;
enum TAX_BASE
{
CN_TAX,
AME_TAX,
JAP_TAX,
JERM_TAX
};
/*1、如果需要新加德国的税金,则enum总需要改
2、客户端程序也需要增加一个else if分支;
3、并且对程序性能也有影响,因为他要一个个if判断过去,如果你给的是Jermany,那么他只能判断到最后一个;
4、如果emun 和 SalesOrder放在不同的文件夹下,那这俩个文件夹都需要被编译;
*/
class SalesOrder
{
public:
double CalculateTax()
{
if (CN_TAX == tax)
{
//...//
cout << "Calculate China tax" << endl;
}
else if (AME_TAX == tax)
{
cout << "Calculate America tax " << endl;
}
else if (JAP_TAX == tax)
{
cout << "Calculate Japan tax" << endl;
}
else if (JERM_TAX == tax)
{
cout << "Calculate Jermany tax" << endl;
}
}
private:
TAX_BASE tax;
};
策略模式的实现:
#pragma once
#include<iostream>
using namespace std;
//基类
class TaxCalFactory
{
public:
virtual double CalculateTax() = 0;
};
class CN_TAX :public TaxCalFactory
{
public:
double CalculateTax()
{
cout << "Calculate China Tax" << endl;
return 0;
}
};
class AME_TAX :public TaxCalFactory
{
public:
double CalculateTax()
{
cout << "Calculate America Tax" << endl;
return 0;
}
};
//在该模式下,不管他要计算哪个国家的税率(比如Jermany)只需要在加一个class Jermany_tax,继承TaxCalFactory,overwrite CalculateTax函数即可。
//就不需要改客户端程序SalesOrder;
//也符合开闭原则;对拓展开放,对修改关闭比如这里对SalesOrder的修改应该关闭,对新增的Jermany_tax开放
class SalesOrder
{
public:
SalesOrder(TaxCalFactory* taxcal) :taxcal(taxcal)
{}
public:
double CalculateTax()
{
taxcal->CalculateTax();
}
private:
TaxCalFactory* taxcal;
};
策略模式可以用在有多种算法,并且需要if 或者case来判断的情况下