什么时候在C ++中调用模板类的静态成员的构造函数?

When do constructors of static members of template classes get called in C++?

当普通类静态成员的制造商被召唤时,有大量的信息。但是,我看到一些奇怪的行为,以缓和阶级。

后续方案的产出应当是什么?(note I use printf to avoid any static initiatization order fiasco complications with std:cout.)

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
#include <iostream>

class B {
public:
  B(const std::string &s) { printf("Hello I am B from %s
"
, s.c_str()); }
};

template<typename T>
class Atempl {
public:
  static B b_;
};

class A {
public:
  static B b_;
};

template<typename T>
B Atempl<T>::b_("Atempl");
B A::b_("A");

class C : public Atempl<int> {
};

int main(int argc, const char *argv[]) {
  return 0;
}

我想输出应该是:

ZZU1

But with G+4.3 on freebsd 7.3 I get:

1
Hello I am B from A

如果我加载线

1
template class Atempl<int>;

一切都很好,我得到了预期的输出。The question is,why doesn't the Declaration of Class C count as an instanction of the Template阿特姆普尔因为B's constructor to be called?这是标准的一部分还是G+4.3中的一个错误?


在类模板中,在执行隐式实例化时,成员是按需实例化的。因为代码不使用静态成员,所以它甚至没有在整个应用程序中实例化。

当你做一个显式的完备性时,整个类和它的所有成员都被实例化,这包括静态成员变量,然后初始化它,你得到你期望的结果。

如果没有显式实例化,您可以执行类似于B* p = &Atempl::b_;的操作(或任何其他使用静态成员的操作)来触发实例化。


初始化类模板模板的静态成员时,未指定的实际上,除非实际使用静态成员,否则不应实例化,因此永远不应初始化。如果你显式实例化模板,强制所有成员,这反过来会强制初始化(但我认为具体什么时候初始化还未指明)。


它们在进程开始后的某个时间由C++运行时调用,并且在调用EDCOX1×1调用之前。"常规"类和类模板实例之间没有区别。调用构造函数的顺序未定义。