C++ 类的静态成员详细讲解[静态成员变量链接错误]
来源:互联网 发布:苹果手机壁纸软件 编辑:程序博客网 时间:2024/06/07 05:36
在C++中,静态成员是属于整个类的而不是某个对象,静态成员变量只存储一份供所有对象共用。所以在所有对象中都可以共享它。使用静态成员变量实现多个对象之间的数据共享不会破坏隐藏的原则,保证了安全性还可以节省内存。
静态成员的定义或声明要加个关键static。静态成员可以通过双冒号来使用即<类名>::<静态成员名>。
在C++中类的静态成员变量和静态成员函数是个容易出错的地方,本文先通过几个例子来总结静态成员变量和成员函数使用规则,再给出一个实例来加深印象。希望阅读本文可以使读者对类的静态成员变量和成员函数有更为深刻的认识。
第一个例子,通过类名调用静态成员函数和非静态成员函数
- class Point
- {
- public:
- void init()
- {
- }
- static void output()
- {
- }
- };
- void main()
- {
- Point::init();
- Point::output();
- }
编译出错:error C2352: 'Point::init' : illegal call of non-static member function
结论1:不能通过类名来调用类的非静态成员函数。
第二个例子,通过类的对象调用静态成员函数和非静态成员函数
将上例的main()改为:
- void main()
- {
- Point pt;
- pt.init();
- pt.output();
- }
编译通过。
结论2:类的对象可以使用静态成员函数和非静态成员函数。
第三个例子,在类的静态成员函数中使用类的非静态成员
- #include <stdio.h>
- class Point
- {
- public:
- void init()
- {
- }
- static void output()
- {
- printf("%d\n", m_x);
- }
- private:
- int m_x;
- };
- void main()
- {
- Point pt;
- pt.output();
- }
编译出错:error C2597: illegal reference to data member 'Point::m_x' in a static member function
因为静态成员函数属于整个类,在类实例化对象之前就已经分配空间了,而类的非静态成员必须在类实例化对象后才有内存空间,所以这个调用就出错了,就好比没有声明一个变量却提前使用它一样。
结论3:静态成员函数中不能引用非静态成员。
第四个例子,在类的非静态成员函数中使用类的静态成员
- class Point
- {
- public:
- void init()
- {
- output();
- }
- static void output()
- {
- }
- };
- void main()
- {
- Point pt;
- pt.output();
- }
编译通过。
结论4:类的非静态成员函数可以调用用静态成员函数,但反之不能。
第五个例子,使用类的静态成员变量
- #include <stdio.h>
- class Point
- {
- public:
- Point()
- {
- m_nPointCount++;
- }
- ~Point()
- {
- m_nPointCount--;
- }
- static void output()
- {
- printf("%d\n", m_nPointCount);
- }
- private:
- static int m_nPointCount;
- };
- void main()
- {
- Point pt;
- pt.output();
- }
按Ctrl+F7编译无错误,按F7生成EXE程序时报链接错误
error LNK2001: unresolved external symbol "private: static int Point::m_nPointCount" (?m_nPointCount@Point@@0HA)
这是因为类的静态成员变量在使用前必须先初始化。
在main()函数前加上int Point::m_nPointCount = 0;
再编译链接无错误,运行程序将输出1。
结论5:类的静态成员变量必须先初始化再使用。
结合上面的五个例子,对类的静态成员变量和成员函数作个总结:
一。静态成员函数中不能调用非静态成员。
二。非静态成员函数中可以调用静态成员。因为静态成员属于类本身,在类的对象产生之前就已经存在了,所以在非静态成员函数中是可以调用静态成员的。
三。静态成员变量使用前必须先初始化(如int MyClass::m_nNumber = 0;),而且是要在函数外部,否则会在linker时出错。
再给一个利用类的静态成员变量和函数的例子以加深理解,这个例子建立一个学生类,每个学生类的对象将组成一个双向链表,用一个静态成员变量记录这个双向链表的表头,一个静态成员函数输出这个双向链表。
- #include <stdio.h>
- #include <string.h>
- const int MAX_NAME_SIZE = 30;
-
- class Student
- {
- public:
- Student(char *pszName);
- ~Student();
- public:
- static void PrintfAllStudents();
- private:
- char m_name[MAX_NAME_SIZE];
- Student *next;
- Student *prev;
- static Student *m_head;
- };
-
- Student::Student(char *pszName)
- {
- strcpy(this->m_name, pszName);
-
- //建立双向链表,新数据从链表头部插入。
- this->next = m_head;
- this->prev = NULL;
- if (m_head != NULL)
- m_head->prev = this;
- m_head = this;
- }
-
- Student::~Student ()//析构过程就是节点的脱离过程
- {
- if (this == m_head) //该节点就是头节点。
- {
- m_head = this->next;
- }
- else
- {
- this->prev->next = this->next;
- this->next->prev = this->prev;
- }
- }
-
- void Student::PrintfAllStudents()代码
- {
- for (Student *p = m_head; p != NULL; p = p->next)
- printf("%s\n", p->m_name);
- }
-
- Student* Student::m_head = NULL;
-
- void main()
- {
- Student studentA("AAA");
- Student studentB("BBB");
- Student studentC("CCC");
- Student studentD("DDD");
- Student student("MoreWindows");
- Student::PrintfAllStudents();
- }
程序将输出:
0
上一篇:[STL]list的erase正确与错误用法
下一篇:C++ 迭代器失效
相关热门文章
- test123
- 编写安全代码——小心有符号数...
- 使用openssl api进行加密解密...
- 一段自己打印自己的c程序...
- sql relay的c++接口
- linux dhcp peizhi roc
- 关于Unix文件的软链接
- 求教这个命令什么意思,我是新...
- sed -e "/grep/d" 是什么意思...
- 谁能够帮我解决LINUX 2.6 10...
给主人留下些什么吧!~~
评论热议
0 0
- [转载]C++ 类的静态成员详细讲解[静态成员变量链接错误
- C++ 类的静态成员详细讲解[静态成员变量链接错误]
- C++ 类的静态成员详细讲解
- C++ 类的静态成员详细讲解
- C++ 类的静态成员详细讲解
- C++ 类的静态成员详细讲解
- C++ 类的静态成员详细讲解
- C++ 类的静态成员详细讲解
- C++ 类的静态成员详细讲解
- C++ 类的静态成员详细讲解
- C++ 类的静态成员详细讲解
- C++ 类的静态成员详细讲解
- C++ 类的静态成员详细讲解
- C++ 类的静态成员详细讲解
- C++ 类的静态成员详细讲解
- C++ 类的静态成员详细讲解
- C++类的静态成员详细讲解
- C++ 类的静态成员详细讲解
- 蓝牙发送多个文件
- Maven构建C++工程的插件-NAR
- VC++生成full dump文件
- 一个支持Git应用编程开发的第三方库(API)
- [STL]list的erase正确与错误用法
- C++ 类的静态成员详细讲解[静态成员变量链接错误]
- java反射详解
- C++ 迭代器失效
- STL容器erase的使用陷阱
- Visual Studio 2012 Ultimate RTM 序列号
- Windows 2003+VS2005+SP1 “无法使用此产品的安装源,请确认安装源存在,并且您可以访问它”的错误
- Symbian OS 源码下载方式
- 链接和装入技术的发展史
- 爱因斯坦名言
原创粉丝点击
热门IT博客
热门问题
老师的惩罚
人脸识别
我在镇武司摸鱼那些年
重生之率土为王
我在大康的咸鱼生活
盘龙之生命进化
天生仙种
凡人之先天五行
春回大明朝
姑娘不必设防,我是瞎子
星汗灿烂幸甚至哉
幸星国际动画学院
星汗灿烂幸甚至哉关心则乱
幸星动画学院
幸星动画培训
真田幸村
网王之幸村被藤蔓侵入
网王之被幸村吃掉
网王之幸村妹妹二三事
暑假回农幸村福之旅蝴蝶
网王之幸村蓝染
幸村
传说中被幸村抛弃的女人
网王之幸村妻子怀孕
赤司幸村的交换人生
真田幸村日文
网王之幸村精溪
稻姬 真田幸村
幸村把龙马拐到立海大
网王之幸村雅炼 绿绿
幸村你放手
网王幸村家懒惰猫的未婚妻
网王之幸村雅炼
网王之我是幸村律
网王之我是幸村的双胞胎
网王之幸村被真田吃掉
网王之我是幸村他哥
幸村你家女主在那边
战国无双2真田幸村攻略
网王黑篮之当幸村转学到洛山
大秦之权掌天下 真田幸村
幸田李梨
幸田莉奈
幸田
幸田李莉美主持在线播放
幸田李莉中文字幕在线播放
幸福归来
幸福
幸福终点站
幸福人生
幸福重奏