策略模式
定義
策略模式定義了算法家族,分別封裝起來,讓他們之間可以相互替換,此模式讓算法的變化,不會影響到客戶端的使用,也稱為政策模式(Policy)。
策略模式主要的作用還是解耦策略的定義、創建和使用,控制代碼的復雜度,讓每個部分都不至於過於復雜、代碼量過多。除此之外,對於復雜代碼來說,策略模式還能讓其滿足開閉原則,添加新策略的時候,最小化、集中化代碼改動,減少引入bug的風險。
優點
1、算法可以自由切換。
2、避免使用多重條件判斷。
3、擴展性良好。
缺點
1、策略類會增多。
2、所有策略類都需要對外暴露。
使用場景
1、如果在一個系統里面有許多類,它們之間的區別僅在於它們的行為,那么使用策略模式可以動態地讓一個對象在許多行為中選擇一種行為。
2、一個系統需要動態地在幾種算法中選擇一種。
3、如果一個對象有很多的行為,如果不用恰當的模式,這些行為就只好使用多重的條件選擇語句來實現。
代碼實現
比如我們在做支付的項目中,對於支付的類型,我們可能會有多種類型,我們可能要做微信支付,支付寶支付,蘋果內購等等一些列的產品。。。
所以我們可以把每種支付產品定義成一種策略,然后根據不同的業務場景選擇不同的支付產品
package main
import (
"fmt"
)
func main() {
payment := NewPayment(&Weixin{
&PaymentConf{
appId: "wx1323234343434",
notifyURL: "weixin.notifyURL.com",
},
})
payment.Pay("小明", 12)
fmt.Println()
apay := NewPayment(&Ali{
&PaymentConf{
appId: "al1323234343434",
notifyURL: "ali.notifyURL.com",
},
})
apay.Pay("小紅", 16)
}
type Context struct {
strategy PaymentStrategy
}
type PaymentConf struct {
appId string
notifyURL string
}
func NewPayment(strategy PaymentStrategy) *Context {
return &Context{
strategy: strategy,
}
}
func (p *Context) Pay(account string, money int) {
p.strategy.Pay(account, money)
}
type PaymentStrategy interface {
Pay(account string, money int)
}
type Weixin struct {
*PaymentConf
}
func (w *Weixin) Pay(account string, money int) {
fmt.Printf("Pay %d元 to %s by weixin", money, account)
}
type Ali struct {
*PaymentConf
}
func (a *Ali) Pay(account string, money int) {
fmt.Printf("Pay %d元 to %s by ali", money, account)
}
來看下結構圖

策略模式和工廠模式的區別
工廠模式
1、目的是創建不同且相關的對象
2、側重於"創建對象"
3、實現方式上可以通過父類或者接口
4、一般創建對象應該是現實世界中某種事物的映射,有它自己的屬性與方法
策略模式
1、目的實現方便地替換不同的算法類
2、側重於算法(行為)實現
3、實現主要通過接口
4、創建對象對行為的抽象而非對對象的抽象,很可能沒有屬於自己的屬性
參考
【策略模式實現代碼】https://github.com/boilingfrog/design-pattern-learning/tree/master/策略模式
【大話設計模式】https://book.douban.com/subject/2334288/
【極客時間】設計模式之美
【工廠模式】https://www.cnblogs.com/ricklz/p/15399178.html
【策略模式】https://boilingfrog.github.io/2021/10/26/使用go實現策略模式/