商场促销--策略模式

#商场促销–策略模式
##商场收银软件
最简单的商场收银软件,只需要输入单价和数量,一个确定按钮来计算出每种商品的费用就行了。

int main()
{
	double total;
	double price, num;
	cout << "请输入价格:";
	cin  >> price;
	cout << "请输入数量:";
	cin >> num;
	total = price * num;
	cout << "总计:" << total;
}

如果商场搞活动,对商品打八折,则怎么做?
很简单的做法就是在price后乘以0.8。如果活动过了怎么办,再改一遍程序代码就好了,然后把所有机器全部安装一次吗?那如果遇到周年庆打5折呢。所以,这时候我们可以考虑用一个下拉框来解决上述所说的问题?
如果遇到满减活动该怎么办呢?
所以,我们可以使用简单工厂模式,先写一个父类,再继承它实现多个打折和返利的子类,利用多态,完成这个代码。
面向对象的编程,并不是类越多越好,类的划分是为了封装,单分类的基础是抽象,具有相同属性和功能的对象的抽象集合才是类。

//基类 CashSuper
class CashSuper
{
public:
	virtual double acceptCash(double money) = 0;
};

//正常价格类 CashNormal
#include "CashSuper.h"
class CashNormal :
    public CashSuper
{
public:
    double acceptCash(double money){
        return money;
    }
};

//打折类 CashRebate
#include "CashSuper.h"
class CashRebate :
    public CashSuper
{
public:
    CashRebate(double moneyRebate){
        this->moneyRebate = moneyRebate;
    }
    double acceptCash(double money){
        return money * moneyRebate;
    }
private:
    double moneyRebate = 1;
};

//满减类 CashReturn
#include "CashSuper.h"
class CashReturn :
    public CashSuper
{
public:
    CashReturn(double moneyCondition, double moneyReturn){
	    this->moneyCondition = moneyCondition;
	    this->moneyReturn = moneyReturn;
    }
    double acceptCash(double money){
        double result = money;
	    if (money >= moneyCondition)
		    result = money - floor(money / moneyCondition) * moneyReturn;
	    return result;
    }

private:
    double moneyCondition;
    double moneyReturn;
};

//简单工厂类 CashFactory
#include "CashSuper.h"

class CashFactory
{
public:
	static CashSuper* createCashAccept(int type) {
		CashSuper* cs = nullptr;
		switch (type)
		{
		case 0:
		{
			cout << "正常收费" << endl;
			cs = new CashNormal();
			break;
		}
		case 1:
		{
			cout << "满300 返 100" << endl;
			CashReturn* cr1 = new CashReturn(300, 100);
			cs = cr1;
			break;
		}
		case 2:
		{
			cout << "打八折" << endl;
			CashRebate* cr2 = new CashRebate(0.8);
			cs = cr2;
			break;
		}
		default:
			cs = new CashNormal();
			break;
		}
		return cs;
	}
};

//实现
int main()
{
	double total = {},totalPrices = 0;
	int type;
	double price, num;
	cout << "请输入价格:";
	cin  >> price;
	cout << "请输入数量:";
	cin >> num;
	cout << "请输入计算方式";
	cin >> type;
	total = price * num;
	CashSuper* csuper = CashFactory::createCashAccept(type);
	totalPrices = csuper->acceptCash(total);
	cout << "总计:" << totalPrices;
}

简单工厂现在差不多已经有了大致的概念了,这个模式只是解决对象创建的问题,如果需要频繁的扩展或维护,就都要改动这个工厂,以致代码需要重新编译部署,这是比较差的处理方式。

策略模式

商场收银时如何促销,用打折还是返利,其实都是一些算法,用工厂来生成算法对象,这没有错,但算法本身只是一种策略,最重要的是这些算法是随时都可能互相替换的,这就是变化点,而封装这些变化点是我们面向对象的一种很重要的思维方式。

#抽象算法类
#include <iostream>
using namespace std;
class Strategy
{
public:
	virtual void AlgorithmInterface(){};
};

#具体算法A
#include "Strategy.h"
class ConcreteStrategyA :
    public Strategy
{
public:
    void AlgorithmInterface()
    {
        cout << "算法A实现" << endl;
    }
};

#具体算法B
#include "Strategy.h"
class ConcreteStrategyB :
    public Strategy
{
public:
    void AlgorithmInterface()
    {
        cout << "算法B实现" << endl;
    }
};

#上下文Context,用一个ConcreteStrategy来配置,维护一个对Strategy对象的引用
#include "Strategy.h"

class Context
{
public:
	Context(Strategy *strategy)
	{
		this->strategy = strategy;
	}

	void ContextInterface()
	{
		strategy->AlgorithmInterface();
	}
private:
	Strategy *strategy;
};

#main使用
	Context *context = new Context(new ConcreteStrategyA());
	context->ContextInterface();
	context = new Context(new ConcreteStrategyB());
	context->ContextInterface();

策略模式是一种定义一系列算法的方法,从概念上来看,所有这些算法完成的都是相同的工作,只是实现不同,它可以以相同的方式调用所有的算法,减少了各种算法类与使用算法类之间的耦合
策略模式的Strategy类层次为Context定义了一系列的可供重用的算法或行为。继承有助于析取出这些算法中的公共功能
策略模式的优点是简化了单元测试,因为每个算法都有自己的类,可以通过自己的接口单独测试
不同的行为堆砌在一个类中时,就很难避免使用条件语句来选择合适的行为。将这些行为封装在一个个独立的Strategy类中,可以在使用这些行为的类中消除条件语句
策略模式就是用来封装算法的,但在实践中,可以用它来封装几乎任何类型的规则,只要在分析工程中听到需要在不同时间应用不同的业务规则,就可以考虑使用策略模式来处理这种变化的可能性

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值