單例模式(Singleton Design Pattern)
單例模式顧名思義,會提供給用戶一個對象(object)的實例(instance) ,並且保證這個實例全局唯一。
單列模式的應用場景很多,比如:
- 當你想用同一個鏈接來訪問數據庫的時候
- 當你用一個ssh 鏈接服務器並執行一些命令,但你不想每次都重開ssh的時候
- 當你想要限制訪問某些資源的時候
目標
我們考慮在需要應用以下規則時使用Singleton模式:
- 我們需要某個特定類型的單個共享值。
- 我們需要將某些類型的對象創建限制爲整個程序中的唯一。
例子
作爲必須確保只有一個實例的對象的一個示例,我們將編寫一個計數器來保存在程序執行期間調用它的次數。不管我們有多少個計數器實例,它們都必須能夠計數相同的值,實例之間必須保持一致。
需求分析
爲了實現這個計數器,我們首先需要分析需求。
- 如果以前沒有創建任何計數器,則使用值0創建一個新計數器
- 如果已經創建了計數器,則返回包含實際計數的實例
- 如果我們調用AddOne方法,計數必須增加1
實現
用Go實現單列模式會與其他模式略微不同, 因爲在Go中是沒有static的變量
package singleton
import "sync"
type Singleton struct{}
var singleton *Singleton
var once sync.Once
func GetInstance() *Singleton {
once.Do(func() {
singleton = &Singleton{}
})
return singleton
}
在這裏我用sync.Once
來保證singleton = &Singleton{}
操作只會被執行一次, sync.Once的用法參考sync
接下來編寫測試來驗證代碼是否與預想的一樣工作
package singleton
import "testing"
func TestSingleton(t *testing.T) {
ins1 := GetInstance()
ins2 := GetInstance()
if ins1 != ins2 {
t.Fatal("instance is not equal")
}
}