C++ 11 Singleton.静态变量是线程安全的吗?为什么?

Dou*_*oid 5 c++11

我刚才读到,这个结构:

const bg::AppSettings& bg::AppSettings::GetInstance()
{
    static AppSettings instance;
    return instance;
}
Run Code Online (Sandbox Code Playgroud)

是一个创建单例的线程安全和工作方式?!我是否正确,每次调用此方法时,静态AppSettings变量都是相同的?!我对这个问题的范围有点困惑......

我的正常方法是使用unique_ptr作为我班级的静态成员......但这似乎有用......有人可以向我解释一下,这里发生了什么?!

顺便说一下:const在这里有意义吗?!

How*_*ant 11

在C++ 11(和转发)中,函数local static的构造AppSettings保证是线程安全的.注意:在VS-2015之前,Visual Studio没有实现C++ 11的这个方面.

编译器将在旁边放置一个隐藏的标志AppSettings,指示它是否:

  • 没有构建.
  • 正在建造中.
  • 建成.

第一个线程将找到标志设置为"未构造"并尝试构造对象.成功构建后,标志将被设置为"已构建".如果另一个线程出现并且发现该标志设置为"正在构造",它将等待该标志设置为"构造".

如果构造因异常而失败,则该标志将被设置为"not construct",并且将在下一次传递时重试构造(在同一线程或不同的线程上).

对象instance将保留为程序的其余部分构建,直到main()返回,此时instance将被销毁.

每次执行任何线程时AppSettings::GetInstance(),它都会引用完全相同的对象.

在C++ 98/03中,不保证结构是线程安全的.

如果AppSettings递归输入构造函数AppSettings::GetInstance(),则行为未定义.

如果编译器可以看到如何构造instance"在编译时",则允许它.

如果AppSettings有一个constexpr构造函数(一个用于构造instance),并且instance是与合格constexpr,编译器要求构成instance在编译时.如果instance在编译时构造,则"not-construct/construct"标志将被优化掉.