Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Go 中使用单例模式 #83

Open
kevinyan815 opened this issue Aug 15, 2022 · 0 comments
Open

Go 中使用单例模式 #83

kevinyan815 opened this issue Aug 15, 2022 · 0 comments

Comments

@kevinyan815
Copy link
Owner

kevinyan815 commented Aug 15, 2022

单例模式,分两种加载模式,下面介绍下 Go 里面怎么使用单例模式。

饿汉模式

适合程序初始化时就确定怎么加载实例的情况

package singleton

// Singleton 饿汉式单例
type Singleton struct{}

var singleton *Singleton

func init() {
	singleton = &Singleton{}
}

// GetInstance 获取实例
func GetInstance() *Singleton {
	return singleton
}

懒汉模式

延迟加载,适合根据传入参数实现定制化的初始化操作。

package singleton

import (
	"sync"
	"sync/atomic"
)


type singleton struct {}

var (
	initialized uint32
	instance *singleton
	mu sync.Mutex
)

func GetInstance() *singleton {

	if atomic.LoadUint32(&initialized) == 1 { // 原子操作
		return instance
	}

	mu.Lock()
	defer mu.Unlock()

	if initialized == 0 {
		instance = &singleton{}
		atomic.StoreUint32(&initialized, 1)
	}

	return instance
}

上面通过了atomic 和 mutex 进行双重检查,保证线程安全,不过可以利用 sync.Once 实现更简洁的版本,这一版最好也记住,有可能面试的时候就不让你用sync.Once实现,sync.Once 内部也是维护了个标志为,用atomic 判断它是否已经执行过函数

Java 里的线程安全的单例也是这么通过volatile+synchronized 双锁检查实现的。

简洁版的懒汉模式单例

package singleton

type singleton struct {}

var instance *singleton
var once sync.Once

func GetInstance() *singleton {
	once.Do(func() {
		instance = &singleton{}
	})
	return instance
}

这里直接上的代码,没有什么废话,如果想看故事版的,可以访问最简单的单例模式,Go版本的实现你写对了吗?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant