第四节 · 公共场所 · 类作用域与静态成员

我们知道,每个对象都有自己的成员变量副本。但有时候,我们需要所有对象共享某些数据,比如统计创建了多少个对象、存储类级别的配置信息等。

这就是静态成员的用武之地。


类作用域

在深入静态成员之前,让我们先了解类作用域

类作用域是指类定义的花括号内的范围。在这个范围内定义的名字,都属于该类:

class MyClass
{
public:
    int value;           // 成员变量,属于 MyClass 作用域
    
    void func()          // 成员函数,属于 MyClass 作用域
    {
        int local = 10;  // 局部变量,属于函数作用域
        value = local;   // 可以访问类成员
    }
    
    typedef int MyInt;   // 类型别名,属于 MyClass 作用域
};

int main()
{
    MyClass obj;
    obj.value = 5;           // 通过对象访问成员
    obj.func();
    MyClass::MyInt x = 10;   // 通过 :: 访问类作用域中的类型
    return 0;
}

在类外引用类作用域中的名字,需要使用作用域解析运算符 ::


静态成员变量

静态成员变量是属于类本身而不是某个对象的变量。所有对象共享同一个静态成员变量。

静态成员变量的特点:

  1. 所有对象共享同一份数据

  2. 在程序启动时创建,程序结束时销毁

  3. 必须在类外定义(除了 const 静态成员)

  4. 可以通过类名或对象访问


静态常量成员

如果静态成员是常量,可以在类内直接初始化:


静态成员函数

静态成员函数是不依赖于任何对象的函数。它没有 this 指针,只能访问静态成员。

静态成员函数的特点:

  1. 没有 this 指针

  2. 只能访问静态成员(变量和函数)

  3. 可以在没有对象的情况下调用

  4. 不能是 const 或 virtual


静态成员的应用场景

1. 单例模式

确保一个类只有一个实例:

2. 工厂方法

3. 工具类


类内静态成员初始化(C++17)

C++17 允许使用 inline 关键字在类内直接定义静态成员:


静态成员让我们能够在类级别存储数据和定义行为,是组织代码的重要工具。

习题

  • 设计一个 BankAccount 类,使用静态成员变量存储银行的总存款金额,每次存款或取款时更新。

  • 设计一个 ID Generator 类,使用静态成员自动为每个对象分配唯一的 ID。

  • 实现一个简单的单例日志类 Logger,提供静态方法记录日志信息。

Last updated