如何在Go语言中实现单例设计模式?

有帮助吗?

解决方案

撇开与否实现Singleton模式是一个好主意的说法,这里有一个可能的实现方式:

package singleton

type single struct {
        O interface{};
}

var instantiated *single = nil

func New() *single {
        if instantiated == nil {
                instantiated = new(single);
        }
        return instantiated;
}

single instantiated是私有的,但New()是公开的。因此,你不能直接实例single不通过New()去,它跟踪与私人布尔instantiated实例的数量。调整single品尝的定义中。

然而,由于其他几个具有指出时,这是不线程安全的,除非你只是在初始化的init()单身。更好的方法是利用sync.Once做艰苦的工作适合你:

package singleton

import "sync"

type single struct {
        O interface{};
}

var instantiated *single
var once sync.Once

func New() *single {
        once.Do(func() {
                instantiated = &single{}
        })
        return instantiated
}

也看到的,只是想一包的的一个单独的哈桑J的建议。最后,不要考虑别人所提出的建议:即单身往往是有问题的执行情况的指标

其他提示

在尝试找到一种让 Go 屈服于你的意愿的方法之前,你可能需要看看一些文章:

总而言之,随着时间的推移,人们发现单例并不是最佳的,恕我直言 尤其 如果您尝试进行任何测试驱动开发:在很多层面上它们几乎和全局变量一样糟糕。

[免责声明:我知道这不是对你问题的严格回答,但它确实相关]

只要把你的变量和函数在包级别。

另见类似的问题:如何使在Python单

我认为,在一个并行的世界我们需要多一点知道这些行不会自动执行:

if instantiated == nil {
    instantiated = new(single);
}

我会按照@marketer的建议,并使用包“同步”

import "sync"

type MySingleton struct {

}

var _init_ctx sync.Once 
var _instance *MySingleton

func New() * MySingleton {
     _init_ctx.Do( func () { _instance = new(MySingleton) }  )
     return _instance 
}

最好的方法将是:

 package singleton

 import "sync"

 type singleton struct {
 }

 var instance *singleton
 var once sync.Once

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

您应该阅读链接

可以使用做初始化一旦包

这将确保您的init方法只被调用一次。

只要有一个单一的静态的,最终的,恒定的,全局的,应用范围所需的对象的实例。

此然而违背了OO范例。它的使用应该限制在原语和不可改变的对象,而不是到可变对象。

你应该知道 Once.Do 认真对待只执行一次代码。这意味着,代码是 总是 只执行一次,即使它可能已经惊慌了:

https://golang.org/pkg/sync/#Once.Do

如果 f (注:一旦逻辑)恐慌,Do 认为它已经返回;Do 的未来调用将返回而不调用 f。

我使用互斥体来确保全局配置变量的唯一初始化以克服此限制:

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top