首页 > 其他分享 >策略模式 trategy

策略模式 trategy

时间:2022-09-25 12:13:07浏览次数:38  
标签:return trategy double Tax 模式 class tax public 策略

“组件协作”模式:

  • 现代软件专业分工之后的第一个结果是“框架与应用程序的划分”,“组件协作”模式通过晚期绑定,来实现框架与应用程序之间的松耦合,是二者之间协作时常用的模式。
  • 典型模式
  1. Template Method
  2. Observer / Event
  3. Strategy

动机(Motivation)

  • 在软件构建过程中,某些对象使用的算法可能多种多样,经常改变,如果将这些算法都编码到对象中,将会使对象变得异常复杂;而且有时候支持不使用的算法也是一个性能负担。
  • 如何在运行时根据需要透明地更改对象的算法?将算法与对象本身解耦,从而避免上述问题?

模式定义

定义一系列算法,把它们一个个封装起来,并且使它们可互相替换(变化)。该模式使得算法可独立于使用它的客户程序(稳定)而变化(扩展,子类化)。——《设计模式》GoF

代码示例

常规想法:

#include <iostream>

using namespace std;

enum TaxBase {
    CN_Tax,
    US_Tax,
    DE_Tax,
    FR_Tax       //更改
};

class SalesOrder
{
public:
    SalesOrder(TaxBase tax)
    {
        this->tax = tax;
    }
private:
    TaxBase tax;
public:
    double CalculateTax() {
        //...
        if (tax == CN_Tax) {
            //CN***********
            return CN_Tax;
        }
        else if (tax == US_Tax) {
            //US***********
            return US_Tax;
        }
        else if (tax == DE_Tax) {
            //DE***********
            return DE_Tax;
        }
        else if (tax == FR_Tax) {  //更改
                                   //...
            return FR_Tax;
        }
        //....
    }
};

int main()
{
    SalesOrder sales(US_Tax);
    double tax = sales.CalculateTax();
    cout << "美国汇率:" << tax << endl;

    getchar();
    return 0;
}

输出:

美国汇率:1

上面的代码,如果要新增一个计算法国的汇率,枚举类内部要修改,计算的函数内部要修改一个 else if。

面向对象:


#include <iostream>

using namespace std;

class StrategyFactory;

// 基类 接口   经常性只放一个方法
class TaxStrategy {
public:
    virtual double Calculate(/*const Context& context*/) = 0;
    virtual ~TaxStrategy() {}
};


class CNTax : public TaxStrategy {
public:
    virtual double Calculate(/*const Context& context*/) {
        //***********
        return 0.0;
    }
};

class USTax : public TaxStrategy {
public:
    virtual double Calculate(/*const Context& context*/) {
        //***********
        return 1.0;
    }
};

class DETax : public TaxStrategy {
public:
    virtual double Calculate(/*const Context& context*/) {
        //***********
        return 2.0;
    }
};



//扩展
//*********************************
class FRTax : public TaxStrategy {
public:
    virtual double Calculate(/*const Context& context*/) {
        //.........
        return 3.0;
    }
};

// 工厂方法,这里是随意写的,意思意思。
class StrategyFactory
{
public:
    StrategyFactory() {}
    ~StrategyFactory() {}
    TaxStrategy * NewStrategy()
    {
        return new USTax;
    }
};

// 上下文
class SalesOrderContext {
private:
    TaxStrategy* strategy;

public:
    // 这里可以用工厂方法,可以由工厂方法决定返回哪个对象。
    SalesOrderContext(StrategyFactory* strategyFactory) {
        this->strategy = strategyFactory->NewStrategy();
    }
    ~SalesOrderContext() {
        delete this->strategy;
    }

    double CalculateTax() {
        //...
        //Context context();

        double val =
            strategy->Calculate(/*context*/); //多态调用
                                          //...
        return val;
    }
};


int main()
{
    StrategyFactory factory;
    SalesOrderContext context(&factory);
    cout << "税率:" << context.CalculateTax() << endl;

    getchar();
    return 0;
}

输出:

税率:1

类图

要点总结

  • Strategy及其子类为组件提供了一系列可重用的算法,从而可以使得类型在运行时方便地根据需要在各个算法之间进行切换。
  • Strategy模式提供了用条件判断语句以外的另一种选择,消除条件判断语句,就是在解耦合。含有许多条件判断语句的代码通常都需要Strategy模式。 // if else if 出现的比较多的时候,就有可能是策略模式的雏形。
  • 如果Strategy对象没有实例变量,那么各个上下文可以共享同一个Strategy对象,从而节省对象开销。 // 如,中国税法全局只有一个的话,用单例模式就好。

标签:return,trategy,double,Tax,模式,class,tax,public,策略
From: https://www.cnblogs.com/huvjie/p/16727371.html

相关文章

  • 建造者模式(创建型)
    建造者模式介绍建造者模式注重的是部件构建的过程,意在通过一步一步地精确构造出一个复杂的对象。可以将建造者模式理解为,假设我们有一个对象需要建立,这个对象是由多个组......
  • 模板方法模式 Template Method
    “组件协作”模式:现代软件专业分工之后的第一个结果是“框架与应用程序的划分”,“组件协作”模式通过晚期绑定,来实现框架与应用程序之间的松耦合,是二者之间协作时常用的......
  • 微服务架构设计模式
    模块化是开发大型、复杂应用程序的基础微服务架构可以消除对某项技术栈的长期依赖微服务架构的弊端和问题:服务的拆分和定义是一项挑战;分布式系统带来的各种复杂性,使开......
  • token 登录模式了解过吗 ?
    token是服务器端生成的一个字符串,当作客服端请求的一个令牌,在第一次登陆成功之后,服务器端会生成一个token,客户端必须要携带token才能请求数据token的具体逻辑如下:......
  • 简明设计模式---桥接模式
    简述类型:结构型目的:通过抽离出多个维度相互组合(聚合)来代替继承,简化系统。话不多说,看个优化案例。优化案例现有系统中,对于画面窗口的边框有一套样式来控制是否有圆......
  • 组合测试术语:Pairwise/All-Pairs、OATS(Orthogonal Array Testing Strategy)
    组合测试组合测试(CombinatorialTest)是一种黑盒测试用例生成方法,主要针对多输入参数组合场景。目前业界较流行的两种组合测试方法,一种是Pairwise/All-Pairs,即配对组合。OA......
  • 访问者模式
    理论访问者模式(Visitor),表示一个作用于某对象结构中的各元素的操作。它使你可以在不改变各元素的类的前提下定义作用于这些元素的新操作。访问者模式的目的:把处理从......
  • 模式识别学习笔记-lecture3-判别函数1
    线性判别函数模式识别系统的主要作用:判别各个模式(样本)所属的类别用判别函数分类的概念判别函数进行分类依赖的因素:判别函数的几何性质:线性的和非线性的函数判别函......
  • 关于mybatis-plus字段更新策略的颗粒度问题
    1.三个可以控制字段更新策略的地方及颗粒度区分1.1mybtis-plus全局配置1.2entity的注解1.3baseMapper.update方法的指定set注意:必须判空set,否则非空时出现两次set语......
  • [Jetpack Compose] 记录一下实现状态栏导航栏透明、应用界面可覆盖两栏、深色浅色模式
    valcolorScheme=when{dynamicColor&&Build.VERSION.SDK_INT>=Build.VERSION_CODES.S->{valcontext=LocalContext.currentif(darkThe......