021 C++的class


作者Lou Xiao, deepseek创建时间2025-04-02 15:22:29更新时间2025-04-02 15:22:29

0. class 特性一览

分类维度成员类型说明示例访问权限是否可继承是否可虚化初始化方式
基础类型数据成员存储对象状态的变量int value;任意(public等)构造函数或初始化列表
成员函数定义对象行为的函数void print() { ... }任意是(虚函数)无需初始化
静态性静态数据成员类级别共享的变量static int count;任意类外初始化(.cpp文件)
非静态数据成员实例级别的变量std::string name;任意构造函数或初始化列表
静态成员函数this指针,只能访问静态成员static void log() { ... }任意无需初始化
访问权限public成员任意位置可访问public: int id;public--
protected成员仅限类内和派生类访问protected: double rate;protected--
private成员仅限类内访问private: int secretCode;private--
特殊成员函数构造函数对象初始化逻辑ClassName(int x) : value(x) {}任意(通常public)自动调用
析构函数资源释放逻辑~ClassName() { delete ptr; }通常public是(虚析构函数)自动调用
拷贝构造函数深拷贝控制ClassName(const ClassName& other);通常public显式或隐式调用
移动构造函数 (C++11)资源转移优化ClassName(ClassName&& other) noexcept;通常public显式调用(std::move触发)
拷贝赋值运算符=操作符重载ClassName& operator=(const ClassName&);通常public显式调用
移动赋值运算符 (C++11)移动语义优化ClassName& operator=(ClassName&&) noexcept;通常public显式调用
虚函数特性虚函数支持动态多态virtual void draw() const;通常public/protected通过派生类覆盖
纯虚函数定义接口规范virtual void serialize() = 0;通常public必须在派生类实现
CV限定const成员函数承诺不修改对象状态int get() const { return value; }任意是(可虚化)-
volatile成员函数处理易变数据void update() volatile { ... }任意-
其他特性mutable成员允许在const函数中修改mutable int cache;任意常规初始化
友元声明授权外部访问私有成员(非类成员)friend class FriendClass;仅类内声明-
内联成员函数编译器展开优化inline void calc() { ... }任意-
constexpr成员函数 (C++11)编译时计算能力constexpr int size() { return N; }任意-
模板成员函数泛型编程支持template<typename T> void process(T);任意-
运算符重载operator重载自定义操作符行为bool operator==(const ClassName&);通常public是(可虚化)-
类型成员嵌套类型类内定义的类型(enum/class/typedef)using Iterator = std::vector<T>::iterator;任意-

关键补充说明:

  1. 存储位置
    - 静态成员:全局数据区(生命周期与程序相同)
    - 非静态成员:对象内存空间(栈/堆)

  2. 虚函数表
    - 虚函数和纯虚函数通过虚函数表(vtable)实现动态绑定

  3. 现代C++扩展
    - noexcept修饰符(C++11):移动操作的异常规范
    - override/final限定符(C++11):显式控制继承行为
    - 委托构造函数(C++11):复用构造函数逻辑

  4. 特殊规则
    - 静态常量整型成员可在类内直接初始化:static const int MAX = 100;
    - 虚函数不能是静态成员函数
    - 友元函数/类不属于类的成员,但拥有访问权限

以下是一个综合示例代码,展示表格中提到的C++类成员特性。代码包含详细注释说明各个知识点:

1.双击鼠标左键复制此行;2.单击复制所有代码。
                                
                                    
1 #include <iostream>
2 #include <string>
3 #include <vector>
4
5 class Entity {
6 // 访问权限分类
7 public:
8 // 基础类型:数据成员 + 成员函数
9 int id; // 公有数据成员
10 void display() const { // const成员函数(CV限定)
11 std::cout << "ID: " << id
12 << ", Name: " << name // 访问私有成员(通过公有接口)
13 << ", Cache: " << cache // mutable成员可修改
14 << "\n";
15 cache = 0; // 允许在const函数中修改mutable成员
16 }
17
18 // 特殊成员函数:构造函数系列
19 Entity(int id, std::string name) // 普通构造函数
20 : id(id), name(name), cache(0) { // 初始化列表
21 ++count; // 访问静态成员
22 }
23
24 Entity(const Entity& other) // 拷贝构造函数
25 : id(other.id), name(other.name), cache(other.cache) {
26 std::cout << "Copy constructor called\n";
27 }
28
29 Entity(Entity&& other) noexcept // 移动构造函数(noexcept C++11)
30 : id(std::move(other.id)),
31 name(std::move(other.name)),
32 cache(std::exchange(other.cache, 0)) {
33 std::cout << "Move constructor called\n";
34 }
35
36 // 运算符重载
37 Entity& operator=(const Entity& rhs) { // 拷贝赋值运算符
38 if (this != &rhs) {
39 id = rhs.id;
40 name = rhs.name;
41 cache = rhs.cache;
42 }
43 return *this;
44 }
45
46 bool operator==(const Entity& other) const { // 运算符重载(比较操作)
47 return id == other.id && name == other.name;
48 }
49
50 // 虚函数特性
51 virtual ~Entity() { // 虚析构函数(支持多态销毁)
52 --count;
53 std::cout << "Entity destroyed\n";
54 }
55
56 virtual void serialize() const { // 虚函数
57 std::cout << "Serializing base entity\n";
58 }
59
60 virtual void update() = 0; // 纯虚函数(接口规范)
61
62 // 静态成员
63 static int count; // 静态数据成员
64 static void logCount() { // 静态成员函数
65 std::cout << "Total entities: " << count << "\n";
66 }
67
68 // 类型成员
69 enum class State { Active, Inactive }; // 嵌套枚举类型
70 using Container = std::vector<Entity>; // 类型别名(C++11 using)
71
72 // 模板成员函数
73 template <typename T>
74 void process(T value) { // 模板成员函数
75 std::cout << "Processing: " << value << "\n";
76 }
77
78 // constexpr成员函数(C++11)
79 constexpr int getCache() const { return cache; }
80
81 protected:
82 std::string name; // 受保护数据成员
83
84 private:
85 // 私有成员与友元
86 mutable int cache; // mutable成员
87 friend void debugEntity(const Entity&); // 友元函数
88 };
89
90 // 静态成员初始化(必须在类外)
91 int Entity::count = 0;
92
93 // 友元函数实现
94 void debugEntity(const Entity& e) {
95 std::cout << "[DEBUG] Private cache: " << e.cache << "\n"; // 访问私有成员
96 }
97
98 // 派生类演示继承和多态
99 class Player : public Entity {
100 public:
101 Player(int id, std::string name, int level)
102 : Entity(id, name), level(level) {}
103
104 // override显式声明(C++11)
105 void serialize() const override {
106 std::cout << "Serializing player (level " << level << ")\n";
107 }
108
109 void update() override { // 实现纯虚函数
110 std::cout << "Updating player...\n";
111 }
112
113 // final阻止进一步重写(C++11)
114 void finalMethod() final {}
115
116 private:
117 int level;
118 };
119
120 int main() {
121 // 静态成员使用
122 Entity::logCount();
123
124 // 对象构造与初始化
125 Entity e1(1, "Test");
126 e1.display();
127 e1.process(3.14); // 模板成员函数调用
128
129 // 拷贝/移动语义
130 Entity e2 = e1; // 调用拷贝构造函数
131 Entity e3 = std::move(e1); // 调用移动构造函数
132
133 // 多态演示
134 Player p1(100, "Hero", 10);
135 Entity* entity = &p1;
136 entity->serialize(); // 动态绑定
137 entity->update();
138
139 // 运算符重载
140 if (e2 == e3) {
141 std::cout << "Entities are equal\n";
142 }
143
144 // 类型成员使用
145 Entity::State state = Entity::State::Active;
146 Entity::Container entities;
147 entities.emplace_back(2, "Object");
148
149 // 友元函数调用
150 debugEntity(p1);
151
152 // 静态成员访问
153 std::cout << "Final entity count: " << Entity::count << "\n";
154 }

该代码演示了以下核心知识点:
1. 访问权限控制(public/protected/private)
2. 构造函数系列(普通/拷贝/移动)
3. 运算符重载(=, ==)
4. 虚函数与纯虚函数(多态实现)
5. 静态成员及其初始化
6. 模板成员函数
7. const成员函数和mutable成员
8. 友元函数访问私有成员
9. 类型成员(枚举、using别名)
10. 现代C++特性(noexcept, override, final)
11. 对象生命周期管理(析构函数调用)
12. 动态多态(通过基类指针调用派生类方法)

编译运行时会依次展示:
- 对象构造/拷贝/移动过程
- 多态方法调用
- 运算符重载比较
- 静态成员计数变化
- 友元函数访问私有成员
- 模板函数实例化等特性

可以通过观察输出顺序和数值变化,直观理解各个类成员的工作机制。


一、类的基本概念

1.1 类定义

1.双击鼠标左键复制此行;2.单击复制所有代码。
                                
                                    
1 class ClassName {
2 // 访问说明符
3 private:
4 // 私有成员(数据+方法)
5 protected:
6 // 受保护成员
7 public:
8 // 公共成员
9 // 构造函数
10 // 析构函数
11 // 成员函数
12 };

1.2 访问控制

访问级别说明
private仅类内成员和友元可访问(默认)
protected类内、派生类和友元可访问
public任何代码均可访问

1.3 成员函数

  • 内联定义:直接在类内实现
  • 外部定义:使用ClassName::methodName()语法
1.双击鼠标左键复制此行;2.单击复制所有代码。
                                
                                    
1 class Rectangle {
2 public:
3 int area() { return width * height; } // 内联
4 void setDimensions(int w, int h);
5 };
6
7 void Rectangle::setDimensions(int w, int h) {
8 width = w;
9 height = h;
10 }

二、对象实例化

2.1 创建对象

1.双击鼠标左键复制此行;2.单击复制所有代码。
                                
                                    
1 ClassName obj; // 栈上分配
2 ClassName *objPtr = new ClassName(); // 堆上分配

2.2 this指针

  • 指向当前对象实例的指针
  • 用于区分成员变量和参数
1.双击鼠标左键复制此行;2.单击复制所有代码。
                                
                                    
1 void ClassName::setValue(int value) {
2 this->value = value;
3 }

三、构造函数与析构函数

3.1 构造函数类型

类型说明示例
默认构造函数无参数ClassName() {}
参数化构造函数带初始化参数ClassName(int a, int b) {}
拷贝构造函数对象复制ClassName(const ClassName &obj) {}
委托构造函数C++11特性,复用其他构造函数ClassName() : ClassName(0,0) {}

3.2 初始化列表

1.双击鼠标左键复制此行;2.单击复制所有代码。
                                
                                    
1 ClassName::ClassName(int a, int b) : memberA(a), memberB(b) {}

3.3 析构函数

1.双击鼠标左键复制此行;2.单击复制所有代码。
                                
                                    
1 ~ClassName() {
2 // 释放资源
3 }

四、静态成员

4.1 静态变量

  • 类所有实例共享
  • 必须在类外初始化
1.双击鼠标左键复制此行;2.单击复制所有代码。
                                
                                    
1 class MyClass {
2 public:
3 static int count;
4 };
5 int MyClass::count = 0;

4.2 静态函数

  • 只能访问静态成员
  • 通过类名调用
1.双击鼠标左键复制此行;2.单击复制所有代码。
                                
                                    
1 class MyClass {
2 public:
3 static void showCount() {
4 cout << count;
5 }
6 };

五、友元机制

5.1 友元函数

1.双击鼠标左键复制此行;2.单击复制所有代码。
                                
                                    
1 class MyClass {
2 private:
3 int secret;
4 friend void friendFunction(MyClass &obj);
5 };
6
7 void friendFunction(MyClass &obj) {
8 obj.secret = 10; // 访问私有成员
9 }

5.2 友元类

1.双击鼠标左键复制此行;2.单击复制所有代码。
                                
                                    
1 class FriendClass {
2 friend class MyClass;
3 // MyClass可访问FriendClass的私有成员
4 };

六、运算符重载

6.1 基本语法

1.双击鼠标左键复制此行;2.单击复制所有代码。
                                
                                    
1 ReturnType operatorOP(ParameterList) {
2 // 实现
3 }

6.2 常见运算符重载

1.双击鼠标左键复制此行;2.单击复制所有代码。
                                
                                    
1 // 加法运算符
2 ClassName operator+(const ClassName &obj) {
3 ClassName temp;
4 temp.value = this->value + obj.value;
5 return temp;
6 }
7
8 // 输入输出流
9 friend ostream& operator<<(ostream &os, const ClassName &obj);

七、继承

7.1 继承类型

继承方式基类public成员基类protected成员
public保持public保持protected
protected变为protected保持protected
private变为private变为private

7.2 派生类定义

1.双击鼠标左键复制此行;2.单击复制所有代码。
                                
                                    
1 class Derived : access-specifier Base {
2 // 新增成员
3 };

7.3 虚函数与多态

1.双击鼠标左键复制此行;2.单击复制所有代码。
                                
                                    
1 class Base {
2 public:
3 virtual void show() { cout << "Base"; }
4 };
5
6 class Derived : public Base {
7 public:
8 void show() override { cout << "Derived"; }
9 };

八、高级特性

8.1 虚析构函数

1.双击鼠标左键复制此行;2.单击复制所有代码。
                                
                                    
1 virtual ~Base() {}

8.2 纯虚函数与抽象类

1.双击鼠标左键复制此行;2.单击复制所有代码。
                                
                                    
1 virtual void func() = 0; // 抽象类至少包含一个纯虚函数

8.3 移动语义(C++11)

1.双击鼠标左键复制此行;2.单击复制所有代码。
                                
                                    
1 ClassName(ClassName&& other) noexcept; // 移动构造函数
2 ClassName& operator=(ClassName&& other) noexcept; // 移动赋值

九、设计原则

  1. 封装性:隐藏实现细节
  2. 单一职责原则:一个类只做一件事
  3. RAII:资源获取即初始化
  4. Liskov替换原则:派生类应可替代基类

十、代码示例

1.双击鼠标左键复制此行;2.单击复制所有代码。
                                
                                    
1 class Animal {
2 protected:
3 string name;
4 public:
5 Animal(string n) : name(n) {}
6 virtual void speak() = 0; // 纯虚函数
7 };
8
9 class Dog : public Animal {
10 public:
11 Dog(string n) : Animal(n) {}
12 void speak() override {
13 cout << name << " says Woof!";
14 }
15 };

注意事项

  1. 遵循三/五法则:如果定义了析构函数/拷贝控制函数,通常需要全部定义
  2. 优先使用初始化列表进行成员初始化
  3. 多态基类应声明虚析构函数
  4. 避免返回内部成员的引用/指针

通过系统学习以上内容,可以掌握C++类的核心机制与高级特性,为面向对象编程打下坚实基础。建议配合实际项目练习,加深理解。

文章目录