设计模式-策略模式

什么是策略模式?

策略模式是一种定义一系列算法的方法,定义了算法家族,分别封装起来,让他们可以相互转化,此模式可以让算法相互转化,且不会影响到算法用户。从概念上来看,所以的算法完成都是相同的工作,只是实现不同。它可以以相同方式调用所有的算法,减少了各种算法类与使用算法类的耦合。
我们用书里面的例子演示一下:假如超市的售货员给顾客结账时,她应该如何选择那种结算方式呢?
假如有:满100减20,满300减70,打5折等等。
我们想,如果用正常的逻辑语句应该怎么写:

if(money>=100){
  	money -=20;
}else if(money>=300){
	money -=70;
}else{
	money/=2;
}

当我们每加入一次结算方式,我们就需要加入一条if-else语句(或者switch语句)实现,然后进行大量的编译过程,浪费大量的人力物力。
既然学习了设计模式,我们就把这个问题系统化。


简单工厂模式实现

使用之前所学的 工厂模式实现.
先设计出来uml图.
在这里插入图片描述这样代码就好实现了如下:

#include<iostream>
#include<cmath>
#include<string>
using namespace std;
class AbstractCashbuy{   //抽象基类 
	public:
		virtual double accpetCash(double money) = 0;
};
class CashBuyNormal :public AbstractCashbuy{
	public:
		virtual double accpetCash(double money){
			return money;
		}
};
class CashBuyDiscount : public AbstractCashbuy{
	private:
		double discount;
	public :
		CashBuyDiscount(double num){
			this->discount = num;
		}
		virtual double accpetCash(double money){
			return money*discount;
		}
};
class CashBuyReduct : public AbstractCashbuy{
	private:
		double full;
		double reduct;
	public :
		CashBuyReduct (double num,double num1){
			this->full = num;
			this->reduct = num1;
		}
		virtual double accpetCash(double money){
			return money-floor(money/full)*reduct;
		}
};
class CashbuyFactory{
	private:
		AbstractCashbuy* CashMethod;
	public :
		//策略工厂模式 
		CashbuyFactory(string str,double discount,double sub=0){
			if(str == "normal"){
				this->CashMethod = new CashBuyNormal;
			}
			else if(str == "discount"){
				this->CashMethod = new CashBuyDiscount(discount);
			}
			else if(str =="reduct"){
				this->CashMethod = new CashBuyReduct(discount,sub);
			}
		}
		double Getmoney(double money){
			return CashMethod->accpetCash(money);
		}
		//工厂模式 
		AbstractCashbuy* CreateCashbuy(string str){
			if(str == "normal"){
				return new CashBuyNormal;
			}
			else if(str == "discount"){
				return new CashBuyDiscount(0.5); 
			}
			else if(str == "reduct"){
				return new CashBuyReduct(500,80);
			}
		}
};
int main(){
	string str,str1,str2;
	str = "normal";
	str1 = "discount";
	str2 = "reduct";
	CashbuyFactory* a= new CashbuyFactory(str2,500,40);
	cout<<a->Getmoney(500)<<endl;
//	AbstractCashbuy* b = a->CreateCashbuy(str);
//	cout<<b->accpetCash(500);
} 

策略模式(Strategy)

策略模式的uml图:
在这里插入图片描述
代码如下:(与工厂模式结合)

#include<iostream>
#include<cmath>
#include<string>
using namespace std;
class AbstractCashbuy{   //抽象基类 
 public:
  virtual double accpetCash(double money) = 0;
};
class CashBuyNormal :public AbstractCashbuy{
 public:
  virtual double accpetCash(double money){
   return money;
  }
};
class CashBuyDiscount : public AbstractCashbuy{
 private:
  double discount;
 public :
  CashBuyDiscount(double num){
   this->discount = num;
  }
  virtual double accpetCash(double money){
   return money*discount;
  }
};
class CashBuyReduct : public AbstractCashbuy{
 private:
  double full;
  double reduct;
 public :
  CashBuyReduct (double num,double num1){
   this->full = num;
   this->reduct = num1;
  }
  virtual double accpetCash(double money){
   return money-floor(money/full)*reduct;
  }
};
class CashbuyFactory{
 private:
  AbstractCashbuy* CashMethod;
 public :
  //策略工厂模式 
  CashbuyFactory(string str,double discount,double sub=0){
   if(str == "normal"){
    this->CashMethod = new CashBuyNormal;
   }
   else if(str == "discount"){
    this->CashMethod = new CashBuyDiscount(discount);
   }
   else if(str =="reduct"){
    this->CashMethod = new CashBuyReduct(discount,sub);
   }
  }
  double Getmoney(double money){
   return CashMethod->accpetCash(money);
  }
 }
 int main(){
 string str,str1,str2;
 str = "normal";
 str1 = "discount";
 str2 = "reduct";
 CashbuyFactory* a= new CashbuyFactory(str2,500,40);
 cout<<a->Getmoney(500)<<endl; //输出460
} 

策略模式的优势

策略模式的Strategy类层次为Context定义了一系列的可供重用的算法。继承有助于析取出这些算法的公共功能,简化了单元测试。并且发现,在策略模式中,我们只需要记住一个CashbuyFactory 类即可,而在工厂模式中,我们需要记住两个类 CashbuyFactory 和 AbstractCashbuy。所有策略模式简化了类的数量。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值