初始化静态数据成员
Initialization of static data member
为什么不进行静态数据成员的默认初始化?在下面的示例
中struct data_member
{
data_member(){ cout << "data_membern"; }
~data_member(){ cout << "~data_membern"; }
};
struct Y
{
static data_member m;
Y(){ cout << "Yn"; }
~Y(){ cout << "~Yn"; }
};
Y y; //call constructor of Y
但是如果我们从data_member m
中删除static
的说明符,它将被默认初始化。
struct data_member
{
data_member(){ cout << "data_membern"; }
~data_member(){ cout << "~data_membern"; }
};
struct Y
{
data_member m;
Y(){ cout << "Yn"; }
~Y(){ cout << "~Yn"; }
};
Y y; //call Y() and data_member()
静态成员必须在类定义之外定义。它将被初始化(也可以默认初始化)。
以下标准草案中关于static
成员变量的描述应该可以解释为什么在类声明中没有默认初始化。
9.4.2静态数据成员2
static
数据成员在其类定义中的声明不是定义,可能是不完整的类型,而不是cv-qualifiedvoid
。static
数据成员的定义应该出现在包含该成员类定义的命名空间作用域中。在命名空间作用域的定义中,static
数据成员的名称应使用::操作符由其类名限定。
struct Y
{
static data_member m;
Y(){ cout << "Yn"; }
~Y(){ cout << "~Yn"; }
};
只有声明了 m
。对于编译器来说,Y::m
是在另一个翻译单元中定义的。由于静态数据成员每个类一个,你必须能够声明它们而不定义它们,否则当你在不同的翻译单元中包含头文件时,你将无法在不违反单一定义规则的情况下将类定义放在头文件中。
data_member Y::m;
这定义了m,并将导致构造函数调用。
static
数据成员在class
定义中声明。它们需要定义(一次)在此之外,通常在相应的cpp
文件中:
data_member Y::m;
在这里你会看到它的默认函数名为
基本答案:类成员就像函数一样。我们有声明和定义。你在类级别"声明"它们的存在,而"定义"是由构造函数完成的。而静态成员则更加复杂。它们不是"与实例相关的",构造函数也不会"定义"它们。你必须在类外自己做:
Type CLASS::member;
顺便说一句,使用静态成员是非常糟糕的做法。
使用静态函数代替:
class Foo{
public:
Type &getMember(){
static Type member;
return member;
}
};
相关文章:
- 静态数据成员的问题-修复链接错误会导致编译器错误
- 静态数据成员模板专用化的实例化点在哪里
- 调用在 HXX 文件中声明的静态数据成员
- 虚拟成员函数的定义是否强制在同一转换单元中动态初始化静态数据成员?
- 错误: 无效使用非静态数据成员"应用程序::应用程序构造函数"
- 静态数据成员:它"const declaration / constexpr definition"起作用?
- 何时需要定义类的静态数据成员 (un/-)
- 为什么静态数据成员不能在c++11中的类中初始化
- 静态数据成员的模板专用化
- 拒绝包含某些公共静态数据成员的类型
- GCC:在调试构建中优化的静态数据成员
- 类模板静态数据成员定义/声明/初始化
- C++ 中的静态数据成员
- 如果类在 C++ 中具有常量或引用类型的非静态数据成员,为什么编译器不提供默认赋值运算符?
- 使用 lambda 函数初始化静态数据成员
- 引用静态数据成员
- 学习C++并在早期示例中遇到错误(在非静态数据成员之前需要构造函数)
- Windows 上的 Clang/LLVM 7 和 8 多次初始化内联静态数据成员(使用 link.exe 和 lld-
- 为什么不能使用"( )"为类的非静态数据成员提供默认值?
- 不带初始值设定项的 constexpr 静态数据成员