c ++:我的singleton线程安全的getInstance()方法是什么?

时间:2011-05-24 20:34:53

标签: c++ boost singleton thread-safety

我目前正在尝试使用boost :: mutex编写线程安全单例(至少在构造和破坏方面)。我读到boost mutex无法静态初始化(我丢失了我读到它的链接,抱歉)所以要解决这个问题,我试过这个,如果构造和破坏的线程安全:

                static T& getInstance()
            {
#ifndef STATIC_VARIABLES_ARE_THREADSAFE
                boost::mutex mutex; 
                boost::lock_guard lock(mutex);
#endif
                static T instance;
                return instance;
            }

是线程安全的,还是应该使用boost :: call_once?是否会提升一次性能优于这种方法?

修改 好吧,我的第一个想法显然不正确。要澄清这个问题。可以安全地初始化boost :: mutex吗?像这样:

class Singleton
{
private:
static boost::mutex m_mutex;

public:
static Singleton & getInstance()
{
    boost::lock_guard lock(m_mutex);
    static T instance;
    return instance;
}

};

这是一种有效的方法还是静态地启动boost :: mutex实际上是不安全的(这是我读过的)?

EDIT2 : 啊,那就是http://uint32t.blogspot.com/2007/12/you-lazy-bastard-part-1.html

的方式

4 个答案:

答案 0 :(得分:3)

由于函数的每个条目都会创建自己的锁,因此锁将完全无用;任意数量的线程都可以进入该函数,锁定不同的锁,同时开始搞乱静态数据。

您可以在文件(或类静态)范围内创建锁;如果您不在main()之前启动线程,这将确保及时创建它。但是,即使在初始化静态数据之后,这也会序列化函数的输入。

为什么不首先在文件(或类静态)范围内定义静态数据?

答案 1 :(得分:1)

GCC提供静态变量的线程安全初始化。 因此,如果您使用GCC,则无需关心静态变量的正确初始化

答案 2 :(得分:0)

您确实需要使用锁定。但是,您建议的boost::mutex方案已被破坏,因为您在堆栈上分配互斥锁,并且多个并发调用方将各自获得自己的互斥锁。

答案 3 :(得分:0)

尝试使用Meyers Singleton实现。

REQ/REP

More info...