1,问完成的需求:
1,统计在程序运行期间某个类的对象数目;
1,静态成员变量满足了这个需求;
2,保证程序的安全性(不能使用全局变量);
3,随时可以获取当前对象的数目;
1,有没有什么特别的地方或边界点没有考虑到呢?
2,解决方案的尝试编程实验:
1 #include <stdio.h> 2 3 class Test 4 { 5 public: 6 static int cCount; 7 public: 8 Test() 9 { 10 cCount++; 11 } 12 ~Test() 13 { 14 --cCount; 15 } 16 int getCount() 17 { 18 return cCount; 19 } 20 }; 21 22 int Test::cCount = 0; 23 24 25 int main() 26 { 27 printf("count = %d ", Test::cCount); // 打印 0; 28 29 Test::cCount = 1000; 30 31 printf("count = %d ", Test::cCount); // 打印 1000; 32 33 return 0; 34 }
1,当没有定义对象时候,应该打印 0,而这里不能满足,完全没办法打印,因 为必须要对象才可以调用打印结果;
2,共有静态成员变量可以解决临界问题,但是不安全,会被误操作;
3,问题分析:我们需要什么?
1,不依赖对象就可以访问静态成员变量;
2,必须保证静态成员变量的安全性;
3,方便快捷的获取静态成员变量的值;
4,静态成员函数:
1,在 C++ 中可以定义静态成员函数:
1,静态成员函数是类中特殊的成员函数;
2,静态成员函数隶属于整个类所有;
3,可以通过类名直接访问公有静态成员函数;
4,可以通过对象名访问公有静态成员函数;
5,静态成员函数的定义:
1,直接通过 static 关键字修饰成员函数:
2,代码示例:
1 class Test 2 { 3 public: 4 static void Func1() {} 5 static int Func2(); 6 }; 7 8 int Test::Func2() 9 { 10 return 0; 11 }
6,静态成员函数示例编程实验:
1 #include <stdio.h> 2 3 class Demo 4 { 5 private: 6 int i; 7 8 public: 9 int getI(); 10 static void StaticFunc(const char* s); 11 static void StaticSetI(Demo& d, int v); 12 // static void StaticSetI(int v); 13 }; 14 15 int Demo::getI() 16 { 17 return i; 18 } 19 20 void Demo::StaticFunc(const char* s) 21 { 22 printf("StaticFunc: %s ", s); 23 } 24 25 void Demo::StaticSetI(Demo& d, int v) 26 { 27 d.i = v; // 这是通过对象名访问,没有直接访问成员变量; 28 } 29 30 /* 31 void Demo::StaticSetI(int v) 32 { 33 i = v; // 编译器显示,在静态成员变量中不能访问成员变量 i;因为静态成员函数不可以直接访问成员变量,访问成员变量需要 this 指针的指向,而这里静态成员函数没有 this 指针; 34 } 35 */ 36 37 int main() 38 { 39 Demo::StaticFunc("main Begin..."); 40 41 Demo d; 42 43 d.StaticSetI(d, 1); // 通过变量名调用静态成员函数 44 45 printf("d.i = %d ", d.getI()); // 打印 1;和不同成员变量使用方法一样; 46 47 Demo::StaticSetI(d, 10); // 通过类名调用静态成员函数; 48 49 printf("d.i = %d ", d.getI()); // 打印 10; 50 51 Demo::StaticFunc("main End..."); 52 53 return 0; 54 }
7,静态成员函数 vs 普通成员函数:
1,可以通过对象名调用静态成员函数;
2,不能访问普通成员变量和成员函数,因为没有 this 指针;
3,静态成员函数存放在代码段,可以供对象和成员函数调用;
8,最后的解决方案编程实验:
1 #include <stdio.h> 2 3 class Test 4 { 5 private: 6 static int cCount; // 不被外界访问,安全;一直存在;被静态成员函数访问,并通过类名调用; 7 8 public: 9 Test() 10 { 11 cCount++; 12 } 13 14 ~Test() 15 { 16 --cCount; 17 } 18 19 static int GetCount() 20 { 21 return cCount; 22 } 23 }; 24 25 int Test::cCount = 0; 26 27 int main() 28 { 29 printf("count = %d ", Test::GetCount()); // 打印 0; 30 31 Test t1; 32 Test t2; 33 34 printf("count = %d ", t1.GetCount()); // 打印 2; 35 printf("count = %d ", t2.GetCount()); // 打印 2; 36 37 Test* pt = new Test(); 38 39 printf("count = %d ", pt->GetCount()); // 打印 3; 40 41 delete pt; 42 43 printf("count = %d ", Test::GetCount()); // 打印 2; 44 45 return 0; 46 }
9,小结:
1,静态成员函数是类中特殊的成员函数;
2,静态成员函数没有隐藏的 this 参数;
1,因此不能访问普通的成员函数及普通的成员变量;
3,静态成员函数可以通过类名直接访问;
4,静态成员函数只能直接访问静态成员变量(函数);