Golang学习笔记_39——策略模式

ops/2025/3/3 20:36:41/

Golang学习笔记_36——装饰器模式
Golang学习笔记_37——外观模式
Golang学习笔记_38——享元模式


文章目录

      • 一、核心概念
        • 1. 定义
        • 2. 解决的问题
        • 3. 核心角色
        • 4. 类图
      • 二、特点分析
      • 三、适用场景
        • 1. 支付系统
        • 2. 数据压缩
        • 3. 游戏AI
        • 4. 折扣计算
      • 四、代码示例(Go语言)
        • 场景:电商会员折扣系统
        • 执行结果
      • 五、高级应用
        • 1. 策略工厂模式
        • 2. 组合策略
      • 六、与其他模式对比
      • 七、总结


一、核心概念

1. 定义

策略模式是一种行为型设计模式,通过定义一系列可互换的算法,并将其封装为独立类,使得算法可以独立于客户端而变化。核心思想是将算法与使用场景解耦,支持运行时动态切换策略。

2. 解决的问题
  • 算法频繁切换:需要根据不同条件选择不同算法(如支付方式、折扣策略)
  • 消除条件判断:避免大量if-elseswitch-case语句
  • 算法复用性:同一算法被多个客户端调用(如排序、压缩算法)
3. 核心角色
角色作用
Strategy策略接口,定义算法的公共方法(如Execute()
ConcreteStrategy具体策略实现类(如支付宝支付、微信支付)
Context上下文类,持有策略引用并执行算法
4. 类图

<a class=策略模式类图" />

@startuml
class Context {- strategy: Strategy+ SetStrategy()+ ExecuteStrategy()
}interface Strategy {+ Execute()
}class ConcreteStrategyA {+ Execute()
}class ConcreteStrategyB {+ Execute()
}Context o--> Strategy
Strategy <|.. ConcreteStrategyA
Strategy <|.. ConcreteStrategyB
@enduml

二、特点分析

优点

  1. 开闭原则:新增策略无需修改现有代码
  2. 代码清晰:消除复杂条件判断,提升可维护性
  3. 灵活扩展:运行时动态切换策略(如游戏AI行为切换)

缺点

  1. 类数量膨胀:每个策略需单独定义类
  2. 客户端耦合:客户端需了解所有策略的存在

三、适用场景

1. 支付系统
  • 策略接口PaymentStrategy
  • 具体策略:信用卡、支付宝、微信支付
  • 动态切换:用户下单时选择支付方式
// 策略接口
type PaymentStrategy interface {Pay(amount float64) string
}// 具体策略:支付宝
type AlipayStrategy struct{}
func (a *AlipayStrategy) Pay(amount float64) string {return fmt.Sprintf("支付宝支付%.2f元", amount)
}
2. 数据压缩
  • 策略接口CompressionStrategy
  • 具体策略:ZIP、RAR、7z算法
  • 按需选择:根据文件类型自动选择压缩算法
// 策略接口
type CompressionStrategy interface {Compress(file string) []byte
}// 具体策略:ZIP压缩
type ZipStrategy struct{}
func (z *ZipStrategy) Compress(file string) []byte {return []byte("ZIP压缩后的数据")
}
3. 游戏AI
  • 策略接口AIBehavior
  • 具体策略:进攻、防御、逃跑模式
  • 动态调整:根据玩家血量切换NPC行为
// 策略接口
type AIBehavior interface {Act() string
}// 具体策略:防御模式
type DefenseBehavior struct{}
func (d *DefenseBehavior) Act() string {return "进入防御状态"
}
4. 折扣计算
  • 策略接口DiscountStrategy
  • 具体策略:普通用户9折、VIP用户8折
  • 组合策略:叠加满减和折扣(见高级应用)

四、代码示例(Go语言)

场景:电商会员折扣系统

在这里插入图片描述

package strategydemo// 策略接口
type DiscountStrategy interface {Calculate(price float64) float64
}// 具体策略:普通会员
type NormalDiscount struct{}
func (n *NormalDiscount) Calculate(price float64) float64 {return price * 0.9 // 9折
}// 具体策略:VIP会员
type VIPDiscount struct{}
func (v *VIPDiscount) Calculate(price float64) float64 {return price * 0.8 // 8折
}// 上下文类
type Order struct {strategy DiscountStrategy
}func (o *Order) SetStrategy(s DiscountStrategy) {o.strategy = s
}func (o *Order) Checkout(price float64) float64 {return o.strategy.Calculate(price)
}// 客户端使用
func TestStrategy() {order := &Order{}// 普通用户order.SetStrategy(&NormalDiscount{})fmt.Printf("普通用户价格: %.2f\n", order.Checkout(100)) // 90.00// 切换为VIP策略order.SetStrategy(&VIPDiscount{})fmt.Printf("VIP用户价格: %.2f\n", order.Checkout(100)) // 80.00
}
执行结果
=== RUN   Test_TestStrategy
普通用户价格: 90.00
VIP用户价格: 80.00
--- PASS: Test_TestStrategy (0.00s)
PASS

五、高级应用

1. 策略工厂模式
// 策略工厂(带注册机制)
type StrategyFactory struct {strategies map[string]DiscountStrategy
}func NewStrategyFactory() *StrategyFactory {return &StrategyFactory{strategies: map[string]DiscountStrategy{"normal": &NormalDiscount{},"vip":    &VIPDiscount{},},}
}// 动态获取策略
func (f *StrategyFactory) GetStrategy(key string) DiscountStrategy {return f.strategies[key]
}// 使用示例
factory := NewStrategyFactory()
order.SetStrategy(factory.GetStrategy("vip"))
2. 组合策略
// 组合折扣(满300减50 + VIP折扣)
type CompositeDiscount struct {strategies []DiscountStrategy
}func (c *CompositeDiscount) Calculate(price float64) float64 {for _, s := range c.strategies {price = s.Calculate(price)}return price
}// 使用示例
composite := &CompositeDiscount{strategies: []DiscountStrategy{&FullReductionStrategy{Threshold: 300, Reduce: 50},&VIPDiscount{},},
}
fmt.Printf("组合折扣价格: %.2f", composite.Calculate(350)) // (350-50)*0.8=240

六、与其他模式对比

模式核心目标关键区别
状态模式对象内部状态改变行为状态转移由内部条件触发
工厂模式创建对象关注对象创建过程
模板方法算法步骤固定通过继承实现代码复用

七、总结

策略模式通过算法封装动态切换,解决了以下问题:

  1. 灵活扩展:新增策略无需修改上下文
  2. 代码复用:相同策略可被多个客户端共享
  3. 条件简化:消除复杂的if-else分支

在Go语言中实现时需注意:

  • 通过接口实现多态,而非继承
  • 使用工厂模式管理策略实例
  • 组合策略实现复杂算法叠加
  • 避免策略类过度细分(如差异过小的策略合并)

http://www.ppmy.cn/ops/162857.html

相关文章

2025年AI网络安全攻防战:挑战深度解析与全链路防御体系构建指南

2025年AI网络安全攻防战:挑战深度解析与全链路防御体系构建指南 引言:AI技术是一把双刃剑 随着ChatGPT、Sora等生成式AI技术的爆发式应用,2025年被称为“AI应用元年”。然而,AI在赋能网络安全防御的同时,也为攻击者提供了新型武器。根据瑞星《2024年中国网络安全报告》,…

Python学习第十八天之深度学习之Tensorboard

Tensorboard 1.TensorBoard详解2.安装3.使用4.图像数据格式的一些理解 后续会陆续在词博客上更新Tensorboard相关知识 1.TensorBoard详解 TensorBoard是一个可视化的模块&#xff0c;该模块功能强大&#xff0c;可用于深度学习网络模型训练查看模型结构和训练效果&#xff08;…

Redis 高可用性:如何让你的缓存一直在线,稳定运行?

&#x1f3af; 引言&#xff1a;Redis的高可用性为啥这么重要&#xff1f; 在现代高可用系统中&#xff0c;Redis 是一款不可或缺的分布式缓存与数据库系统。无论是提升访问速度&#xff0c;还是实现数据的高效持久化&#xff0c;Redis 都能轻松搞定。可是&#xff0c;当你把 …

面试八股文--数据库基础知识总结(2) MySQL

本文介绍关于MySQL的相关面试知识 一、关系型数据库 1、定义 关系型数据库&#xff08;Relational Database&#xff09;是一种基于关系模型的数据库管理系统&#xff08;DBMS&#xff09;&#xff0c;它将数据存储在表格&#xff08;表&#xff09;中&#xff0c;并通过表格…

DeepSeek 接入PyCharm实现AI编程!(支持本地部署DeepSeek及官方DeepSeek接入)

前言 在当今数字化时代&#xff0c;AI编程助手已成为提升开发效率的利器。DeepSeek作为一款强大的AI模型&#xff0c;凭借其出色的性能和开源免费的优势&#xff0c;成为许多开发者的首选。今天&#xff0c;就让我们一起探索如何将DeepSeek接入PyCharm&#xff0c;实现高效、智…

Android NDK打包封装教程与优化技巧

关于NDK打包封装的问题。首先,用户可能不太清楚NDK的基本概念,所以我应该先解释NDK是什么以及它的作用。然后,用户可能想知道如何在Android项目中使用NDK,所以需要分步骤说明配置过程,包括安装NDK、配置CMake或ndk-build,创建JNI接口,编写C/C++代码,编译和打包。 接下…

LeetCode 贪心算法经典题目 (C++实现)

121. 买卖股票的最佳时机 题目描述 给定一个数组 prices &#xff0c;它的第 i 个元素 prices[i] 表示一支给定股票第 i 天的价格。 你只能选择 某一天 买入这只股票&#xff0c;并选择在 未来的某一个不同的日子 卖出该股票。设计一个算法来计算你所能获取的最大利润。 返…

Hive-08之数据仓库之建模、分析

一、目标 掌握数据仓库基本概念熟悉数据仓库的模型建立 二、知识要点 1. 数据仓库基本介绍 英文名称为Data Warehouse&#xff0c;可简写为DW或DWH。数据仓库的目的是构建面向分析的集成化数据环境&#xff0c;为企业提供决策支持&#xff08;Decision Support&#xff09;…