策略模式定义了算法家族,在调用算法家族的时候不感知算法的变化,客户也不会受到影响。

下面用《大话设计模式》中的一个实例进行改写。

例:超市中经常进行促销活动,促销活动的促销方法就是一个个策略,如“满一百减20”,“打八折”等。现在实现策略模式,用CashContext生产策略,并完成策略的调用。

1.首先定义所有策略的接口。

package cash

type cashSuper interface {
AcceptMoney(money float64) float64
}

2.定义三个子类,实现此接口

package cash

//普通情况,没有折扣
type cashNormal struct {
} func newCashNormal() cashNormal {
instance := new(cashNormal)
return *instance
} func (c cashNormal) AcceptMoney(money float64) float64 {
return money
}
package cash

//打折,传入打折的折扣,如0.8
type cashRebate struct {
Rebate float64 //折扣
} func newCashRebate(rebate float64) cashRebate {
instance := new(cashRebate)
instance.Rebate = rebate
return *instance
} func (c cashRebate) AcceptMoney(money float64) float64 {
return money * c.Rebate
}
package cash

//直接返利,如满100返20
type cashReturn struct {
MoneyCondition float64
MoneyReturn float64
} func newCashReturn(moneyCondition float64, moneyReturn float64) cashReturn {
instance := new(cashReturn)
instance.MoneyCondition = moneyCondition
instance.MoneyReturn = moneyReturn
return *instance
} func (c cashReturn) AcceptMoney(money float64) float64 {
if money >= c.MoneyCondition {
moneyMinus := int(money / c.MoneyCondition)
return money - float64(moneyMinus)*c.MoneyReturn
}
return money
}

3.最重要的时刻来临了,定义CashContext结构,用来做策略筛选

package cash

type CashContext struct {
Strategy cashSuper
} func NewCashContext(cashType string) CashContext {
c := new(CashContext)
//这里事实上是简易工厂模式的变形,用来生产策略
switch cashType {
case "打八折":
c.Strategy = newCashRebate(0.8)
case "满一百返20":
c.Strategy = newCashReturn(100.0, 20.0)
default:
c.Strategy = newCashNormal()
}
return *c
} //在策略生产成功后,我们就可以直接调用策略的函数。
func (c CashContext) GetMoney(money float64) float64 {
return c.Strategy.AcceptMoney(money)
}

4.调用测试

package main

import (
"cash"
"fmt"
) func main() {
money := 100.0
cc := cash.NewCashContext("打八折")
money = cc.GetMoney(money)
fmt.Println("100打八折实际金额为", money) money = 199
cc = cash.NewCashContext("满一百返20")
money = cc.GetMoney(money)
fmt.Println("199满一百返20实际金额为", money) money = 199
cc = cash.NewCashContext("没有折扣")
money = cc.GetMoney(money)
fmt.Println("199没有折扣实际金额为", money) } /***************************************
输出:
100打八折实际金额为 80
199满一百返20实际金额为 179
199没有折扣实际金额为 199
*/

总结:策略模式解除了客户对策略的感知,所有策略,甚至cashSuper皆为私有。只需要暴露CashContext就可以生成策略。降低了耦合。

Go---设计模式(策略模式)的更多相关文章

  1. 15. 星际争霸之php设计模式--策略模式

    题记==============================================================================本php设计模式专辑来源于博客(jymo ...

  2. [.net 面向对象程序设计深入](24)实战设计模式——策略模式(行为型)

    [.net 面向对象程序设计深入](24)实战设计模式——策略模式(行为型) 1,策略模式定义 策略模式定义了一系列的算法,并将每一个算法封装起来,而且使它们还可以相互替换.策略模式让算法独立于使用它 ...

  3. linkin大话设计模式--策略模式

    linkin大话设计模式--策略模式 Strategy [ˈstrætədʒi]  策略 策略模式用于封装系列的算法,这些算法通常被封装在一个称为Context的类中,客户端程序可以自由的选择任何一种 ...

  4. [.net 面向对象程序设计深入](26)实战设计模式——策略模式 Strategy (行为型)

    [.net 面向对象程序设计深入](26)实战设计模式——策略模式 Strategy (行为型) 1,策略模式定义 策略模式定义了一系列的算法,并将每一个算法封装起来,而且使它们还可以相互替换.策略模 ...

  5. 设计模式-策略模式(Strategy Model)

    1.概述     在开发过程中常常会遇到类似问题,实现一个功能的时候往往有多种算法/方法(策略),我们可以根据环境的不同来使用不同的算法或策略来实现这一功能.     如在人物比较排序的实现中,我们有 ...

  6. java设计模式 策略模式Strategy

    本章讲述java设计模式中,策略模式相关的知识点. 1.策略模式定义 策略模式,又叫算法簇模式,就是定义了不同的算法族,并且之间可以互相替换,此模式让算法的变化独立于使用算法的客户.策略模式属于对象的 ...

  7. [Head First设计模式]策略模式

    系列文章 [Head First设计模式]山西面馆中的设计模式——装饰者模式 [Head First设计模式]山西面馆中的设计模式——观察者模式 [Head First设计模式]山西面馆中的设计模式— ...

  8. javascript 设计模式-----策略模式

    在<javascript设计模式>中,作者并没有向我们介绍策略模式,然而它却是一种在开发中十分常见的设计模式.最常见的就是当我们遇到一个复杂的表单验证的时候,常常需要编写一大段的if和el ...

  9. JAVA 设计模式 策略模式

    用途 Title 它定义了算法家族,分别封装起来,让它们之间可以互相替换,此模式让算法的变化,不会影响到使用算法的客户. 策略模式是一种行为型模式. 结构

  10. PHP设计模式-策略模式 转

    策略模式(Strategy Pattern) 策略模式是对象的行为模式,用意是对一组算法的封装.动态的选择需要的算法并使用. 策略模式指的是程序中涉及决策控制的一种模式.策略模式功能非常强大,因为这个 ...

随机推荐

  1. 用python+pygame写贪吃蛇小游戏

    因为python语法简单好上手,前两天在想能不能用python写个小游戏出来,就上网搜了一下发现了pygame这个写2D游戏的库.了解了两天再参考了一些资料就开始写贪吃蛇这个小游戏. 毕竟最开始的练手 ...

  2. centos6上安装mysql8.0版本

    本博客是采用yum源的方式安装,非常的方便和快捷.(redhat 与centos7 等操作系统都可以采用此方法,步骤大体一致) mysql官网地址:   https://dev.mysql.com 开 ...

  3. 数组、list排序

    //数字排序 int[] intArray = new int[] {4, 1, 3, -23}; Arrays.sort(intArray); 输出: [-23, 1, 3, 4] //字符串排序, ...

  4. #PHP#微信支付 第二篇 JSAPI 调用统一下单接口获取预支付交易数据

    上一篇讲到成功获取 openid,本篇要调用微信统一接口创建预支付交易单,并获取到相关数据,以便(后边)在微信内调起H5支付 第三步,调用微信统一下单接口创建预支付交易单 微信统一下单API是微信支付 ...

  5. mybatis-4 mybatis与spring结合使用及原理

    1.创建项目maven,方便依赖下载.使用的jar如下: <dependencies> <dependency> <groupId>org.springframew ...

  6. 解决普遍pc端公共底部永远在下面框架

    <div style="width: 90%;height: 3000px;margin: 0 auto; background: red;"></div> ...

  7. Linux用户和组的概念

    目 录 第1章 用户和组存在的关系    1 1.1 我们现在所使用的操作系统都是多用户操作系统    1 1.2 id命令查看当前登陆的用户信息    1 1.3 用户UID的分类    1 1.4 ...

  8. JS应用之正则表达式

    定义 正则表达式是用于匹配字符串中字符组合的模式. 创建正则表达式 两种方式: 1.new RegExp() let pattern1 = new RegExp('cat'); //第一个参数字符串 ...

  9. qt c++对象头文件如何相互包含

    今天在写qt时,遇到了两个类相互包含的问题,类A要用到类B,类B要用到类A. 类A:a.h #ifndef A_H #define A_H #include <b.h> class A { ...

  10. CSS--浮动与定位

    *浮动布局能够实现横向多列布局. 1.在网页中,元素有三种布局模型: 1.流动模型(Flow) 2.浮动模型 (Float) 3.层模型(Layer) 流动(Flow)是默认的网页布局模式.流动布局模 ...