Go语言实现单例模式

基本概念

简单来说就是保证一个类仅有一个实例,并提供一个访问它的全局访问点

注意点

1. 某个类只能有一个实例

2. 这个类必须自行创建这个实例

3. 这个类必须自行向整个系统提供这个实例

分类

单例模式主要分为饿汉式跟懒汉式写法

1. 饿汉式:类在编译时创建自己的实例。由于是静态初始化,它是类一加载就实例化的对象,所以会占用资源。简单理解就是实例已经提前创建好了,GetInstance()只是获取实例返回。

2. 懒汉式:类在运行时创建自己的实例。由于是在运行时才创建自己实例,会面临多线程访问的安全问题,需要处理才能保证安全。

代码实例

饿汉式单例模式

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

var s *singleton

type singleton struct {
}

func GetInstance() *singleton {
	return s
}

func main() {
	a1 := GetInstance()
	a2 := GetInstance()
	fmt.Println(a1 == a2) //结果为true
}

懒汉式单例模式

普通情况下的单例模式

var s *singleton

type singleton struct {

}

func GetInstance() *singleton {
	if s == nil{
		s = &singleton{}
	}
	return s
}

func main()  {
	a1 := GetInstance()
	a2 := GetInstance()
	fmt.Println(a1 == a2) //结果为true
}

并发情况下的单例模式

例1:

var (
	s *singleton
	lock = &sync.Mutex{}
)

type singleton struct {
}

func GetInstance() *singleton {
	lock.Lock()
	defer lock.Unlock()
	if s == nil {
		s = &singleton{}
	}
	return s
}

例2:

例1的改进版,第一个if是先判断实例是否存在再进行处理,避免每次调用函数就进行处理,影响性能。第二个if是为了应付并发的情况。

var (
	s    *singleton
	lock = &sync.Mutex{}
)

type singleton struct {
}

func GetInstance() *singleton {
	if s == nil {
		lock.Lock()
		defer lock.Unlock()
		if s == nil {
			s = &singleton{}
		}
	}
	return s
}

例3:

优雅的方式,使用Go独特的机制sync.Once,保证实例化代码只会执行一次

var (
	s    *singleton
	once = &sync.Once{}
)

type singleton struct {
}

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

注意:上面在定义singleton这个结构体时都是用小写字母开头,是避免它被其它地方调用,在go语言中,大写字母开头的写法类似于公共变量。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值