C++空类编译器自动生成的6个成员函数
来源:互联网 发布:慈星股份人工智能 编辑:程序博客网 时间:2024/05/23 20:37
一、问题
在C++中,编译器会为空类提供哪些默认成员函数?分别有什么样的功能呢?
二、详解
1、空类,声明时编译器不会生成任何成员函数
对于空类,编译器不会生成任何的成员函数,只会生成1个字节的占位符。
有时可能会以为编译器会为空类生成默认构造函数等,事实上是不会的,编译器只会在需要的时候生成6个成员函数:一个缺省的构造函数、一个拷贝构造函数、一个析构函数、一个赋值运算符、一对取址运算符和一个this指针。
代码:
#include <iostream>using namespace std;class Empty_one{};class Empty_two{};class Empty_three{ virtual void fun() = 0;};class Empty_four : public Empty_two, public Empty_three{};int main(){ cout<<"sizeof(Empty_one):"<<sizeof(Empty_one)<<endl; cout<<"sizeof(Empty_two):"<<sizeof(Empty_two)<<endl; cout<<"sizeof(Empty_three):"<<sizeof(Empty_three)<<endl; cout<<"sizeof(Empty_four):"<<sizeof(Empty_four)<<endl; return 0;}运行结果:
分析:
类Empty_one、Empty_two是空类,但空类同样可以被实例化,而每个实例在内存中都有一个独一无二的地址,为了达到这个目的,编译器往往会给一个空类隐含的加一个字节,这样空类在实例化后在内存得到了独一无二的地址,所以sizeof(Empty_one)和sizeof(Empty_two)的大小为1。
类Empty_three里面因有一个纯虚函数,故有一个指向虚函数的指针(vptr),64位系统分配给指针的大小为8个字节,所以sizeof(Empty_three)的大小为8。
类Empty_four继承于Empty_two和Empty_three,编译器取消Empty_two的占位符,保留一虚函数表,故大小为8。
2、空类,定义时会生成6个成员函数
当空类Empty_one定义一个对象时Empty_one pt;sizeof(pt)仍是为1,但编译器会生成6个成员函数:一个缺省的构造函数、一个拷贝构造函数、一个析构函数、一个赋值运算符、两个取址运算符。
class Empty{};等价于:
class Empty{ public: Empty(); //缺省构造函数 Empty(const Empty &rhs); //拷贝构造函数 ~Empty(); //析构函数 Empty& operator=(const Empty &rhs); //赋值运算符 Empty* operator&(); //取址运算符 const Empty* operator&() const; //取址运算符(const版本)};使用时的调用情况:
Empty *e = new Empty(); //缺省构造函数delete e; //析构函数Empty e1; //缺省构造函数 Empty e2(e1); //拷贝构造函数e2 = e1; //赋值运算符Empty *pe1 = &e1; //取址运算符(非const)const Empty *pe2 = &e2; //取址运算符(const)
C++编译器对这些函数的实现:
inline Empty::Empty() //缺省构造函数{}inline Empty::~Empty() //析构函数{}inline Empty *Empty::operator&() //取址运算符(非const){ return this; } inline const Empty *Empty::operator&() const //取址运算符(const){ return this;}inline Empty::Empty(const Empty &rhs) //拷贝构造函数{ //对类的非静态数据成员进行以"成员为单位"逐一拷贝构造 //固定类型的对象拷贝构造是从源对象到目标对象的"逐位"拷贝}inline Empty& Empty::operator=(const Empty &rhs) //赋值运算符{ //对类的非静态数据成员进行以"成员为单位"逐一赋值 //固定类型的对象赋值是从源对象到目标对象的"逐位"赋值。}例如:m是类C中的一个类型为T的非静态成员变量,若C没有声明拷贝构造函数(赋值运算符), m将会通过T的拷贝构造函数(赋值运算符)被拷贝构造(赋值);该规则递归应用到m的数据成员,直到找到一个拷贝构造函数(赋值运算符)或固定类型(例如:int、double、指针等)为止。
三、总结
(1)上述运行结果依赖于编译器和64位、32位不同的系统。
(2)本博文只是总结一些C++特性,也有无法理解的地方,不足之处还请指出,在此先感谢!
- C++空类编译器自动生成的6个成员函数
- C++空类编译器自动生成的6个成员函数
- C++空类编译器自动生成的6个成员函数
- C++空类编译器自动生成的6个成员函数
- C++空类编译器自动生成的6个成员函数
- C++空类产生哪些成员函数 || C++类可以自动生成的6个成员函数
- Effective C++(6) 如何拒绝编译器的自动生成函数
- C++空类,编译器默认产生的成员函数
- 隐式成员函数:由编译器自动生成的函数(自动是罪恶的根
- 类的设计--编译器生成的成员函数
- 当心编译器生成的隐含成员函数
- <Effective C++>:Item 6 :明确拒绝不想编译器自动生成的函数
- 定义一个C++空类,编译器会自动生成哪几个函数?
- 【C++缺省函数】 空类默认产生的6个类成员函数
- 【C++缺省函数】 空类默认产生的6个类成员函数
- C++空类默认产生6个类成员函数
- C++编译器为类自动生成的函数
- EffictiveC++屏蔽编译器自动生成的函数
- WEB架构师成长之路——走正确的路
- sgu204:Little Jumper(数学分析+物理分析)
- 呼啦啦啦~
- Linux 基金会宣布联合 edX 提供免费 Linux 课程
- HTML5+开发移动app教程2-原理介绍
- C++空类编译器自动生成的6个成员函数
- UNIX网络编程——原始套接字的魔力【下】
- Android WebRTC 音视频开发总结(二)
- 配置vs2013的 [头文件] [静态库] [动态库] 路径
- Sql Server数据库事务
- [JAVA加解密]数字签名
- 家
- centos65安装简测mysql cluster 7.3.7
- OpenFire源码学习之三十一:使用Tsung测试openfire(上)