迈耶斯·辛格尔顿取决于local static variable initialization is atomic的事实。
我正在构建类似的东西,但我希望单例实际上是许多派生类型中的一种。基类getInstance()
方法应该调用将返回适当类型的工厂。
我的第一个想法是
static Foo *instance = FooFactory(...);
8.5p2的N3337似乎表明这是严格初始化而不是初始化和赋值,我将其解释为整个语句是原子的。它是否正确?
如果不是声明
static Foo *instance(FooFactory(...));
与众不同?
编辑8.5.2 - > 8.5.p2
答案 0 :(得分:1)
从C ++ 11开始,函数本地的静态变量的初始化是原子的和线程安全的,所以是的,你的代码行是线程安全的,实际上是等价的。 (语法方面,您的第一个版本调用复制构造函数,但没有编译器会生成它)。
但是,目前尚不清楚将为您的工厂功能提供哪些参数以及将从哪些参数中取出?
答案 1 :(得分:1)
variable_type variable_name = initializer
始终是初始化,而不是默认构造和赋值。 [dcl.init] / 15有
以
形式出现的初始化T x = a;
以及参数传递,函数返回,抛出异常(15.1),处理异常(15.3)和聚合成员初始化(8.5.1)称为复制初始化。 [注意:复制初始化可以调用移动(12.8)。 - 后注]
答案 2 :(得分:1)
8.5.2是" [dcl.init.string]",似乎并不相关。我认为你的意思是8.5 para2。
是的,这是严格的初始化(特别是复制初始化 - 见8.5 para14)。
如果声明在函数内,那么,如the answer to the linked question shows,一切都很好。
但是,如果这是命名空间范围内的静态变量,那么我就看不到任何需要初始化的线程安全的东西。 (如果初始化创建线程,这只是一个问题 - 但我敢打赌它。)