Go設(shè)計(jì)模式之策略模式講解和代碼示例
Go 策略模式講解和代碼示例
策略是一種行為設(shè)計(jì)模式, 它將一組行為轉(zhuǎn)換為對(duì)象, 并使其在原始上下文對(duì)象內(nèi)部能夠相互替換。
原始對(duì)象被稱為上下文, 它包含指向策略對(duì)象的引用并將執(zhí)行行為的任務(wù)分派給策略對(duì)象。 為了改變上下文完成其工作的方式, 其他對(duì)象可以使用另一個(gè)對(duì)象來替換當(dāng)前鏈接的策略對(duì)象。
概念示例
思考一下構(gòu)建內(nèi)存緩存的情形。 由于處在內(nèi)存中, 故其大小會(huì)存在限制。 在達(dá)到其上限后, 一些條目就必須被移除以留出空間。 此類操作可通過多種算法進(jìn)行實(shí)現(xiàn)。 一些流行的算法有:
- 最少最近使用 (LRU): 移除最近使用最少的一條條目。
- 先進(jìn)先出 (FIFO): 移除最早創(chuàng)建的條目。
- 最少使用 (LFU): 移除使用頻率最低一條條目。
問題在于如何將我們的緩存類與這些算法解耦, 以便在運(yùn)行時(shí)更改算法。 此外, 在添加新算法時(shí), 緩存類不應(yīng)改變。
這就是策略模式發(fā)揮作用的場(chǎng)景。 可創(chuàng)建一系列的算法, 每個(gè)算法都有自己的類。 這些類中的每一個(gè)都遵循相同的接口, 這使得系列算法之間可以互換。 假設(shè)通用接口名稱為 evictionAlgo
移除算法 。
現(xiàn)在, 我們的主要緩存類將嵌入至 evictionAlgo
接口中。 緩存類會(huì)將全部類型的移除算法委派給 evictionAlgo
接口, 而不是自行實(shí)現(xiàn)。 鑒于 evictionAlgo
是一個(gè)接口, 我們可在運(yùn)行時(shí)將算法更改為 LRU、 FIFO 或者 LFU, 而不需要對(duì)緩存類做出任何更改。
evictionAlgo.go: 策略接口
package main // 策略接口 type EvictionAlgo interface { evict(c *Cache) }
fifo.go:具體策略
package main import "fmt" type Fifo struct{} func (l *Fifo) evict(c *Cache) { fmt.Println("Evicting by fifo strtegy") }
lru.go:具體策略
package main import "fmt" type Lru struct{} func (l *Lru) evict(c *Cache) { fmt.Println("Evicting by lru strtegy") }
lfu.go:具體策略
package main import "fmt" type Lfu struct{} func (l *Lfu) evict(c *Cache) { fmt.Println("Evicting by lfu strtegy") }
cache.go:背景
package main type Cache struct { storage map[string]string evictionAlgo EvictionAlgo capacity int macCapacity int } // 初始化的時(shí)候?qū)⒉呗宰⑷氲?cache 中 func initCache(e EvictionAlgo) *Cache { storage := make(map[string]string) return &Cache{ storage: storage, evictionAlgo: e, capacity: 0, macCapacity: 2, } } // 動(dòng)態(tài)修改策略 func (c *Cache) setEvictionAlgo(e EvictionAlgo) { c.evictionAlgo = e } func (c *Cache) add(key, value string) { // 如果緩存中的容量等于了最大容量,則需要執(zhí)行策略來移除 s if c.capacity == c.macCapacity { c.evict() } c.capacity++ c.storage[key] = value } func (c *Cache) evict() { c.evictionAlgo.evict(c) c.capacity-- } func (c *Cache) get(key string) { delete(c.storage, key) }
main.go:客戶端代碼
package main func main() { lfu := &Lfu{} cache := initCache(lfu) cache.add("a", "1") cache.add("b", "2") cache.add("c", "3") lru := &Lru{} cache.setEvictionAlgo(lru) cache.add("d", "4") fifo := &Fifo{} cache.setEvictionAlgo(fifo) cache.add("e", "5") }
output.txt:執(zhí)行結(jié)果
Evicting by lfu strtegy
Evicting by lru strtegy
Evicting by fifo strtegy
到此這篇關(guān)于Go設(shè)計(jì)模式之策略模式講解和代碼示例的文章就介紹到這了,更多相關(guān)Go策略模式內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
Go語言實(shí)現(xiàn)的一個(gè)簡(jiǎn)單Web服務(wù)器
這篇文章主要介紹了Go語言實(shí)現(xiàn)的一個(gè)簡(jiǎn)單Web服務(wù)器,本文先是給出一個(gè)使用http包建立的Web服務(wù)器源碼,并對(duì)比了其它編程語言,需要的朋友可以參考下2014-10-10Golang自動(dòng)追蹤GitHub上熱門AI項(xiàng)目
這篇文章主要為大家介紹了Golang自動(dòng)追蹤GitHub上熱門AI項(xiàng)目,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2023-12-12Go語言中關(guān)閉帶緩沖區(qū)的頻道實(shí)例分析
這篇文章主要介紹了Go語言中關(guān)閉帶緩沖區(qū)的頻道,實(shí)例分析了帶緩沖區(qū)頻道的原理與用法,以及關(guān)閉帶緩沖區(qū)頻道的技巧,具有一定參考借鑒價(jià)值,需要的朋友可以參考下2015-02-02etcd通信接口之客戶端API核心方法實(shí)戰(zhàn)
這篇文章主要為大家介紹了etcd通信接口之客戶端API核心方法實(shí)戰(zhàn),有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2022-06-06Golang基于JWT與Casbin身份驗(yàn)證授權(quán)實(shí)例詳解
這篇文章主要為大家介紹了Golang基于JWT與Casbin實(shí)現(xiàn)身份驗(yàn)證授權(quán)實(shí)例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2022-08-08