c++对象
对象的大小
常规
初学c++的时候,我们经常对类实际的大小感到困惑,当类中即有成员和函数的时候,这个类的大小到底是多大呢?我们可以使用sizeof来查看
类对象的大小。
#include<iostream>
#include<stdio.h>
using namespace std;
class B{
private:
int b;
public:
int getB(){
return b;
}
};
int main(){
B b;
printf("size of B: %d\n", sizeof(b));
}
这个类的大小输出是4,那么由此我们可以知道类中的函数是不占类的大小的。
特殊
那么有一下几种特殊情况,我们思考类的大小是多少呢?
- 空类
- 空结构体
- 类中只有成员函数,没有变量
#include<iostream>
#include<stdio.h>
using namespace std;
//空结构体A大小是1
typedef struct A{
// int a;
};
//空类B的大小是1
class B{
};
//有一个函数的类的大小是1
typedef struct C{
void test(){
}
};
int main(){
A a;
B b;
C c;
printf("size of A: %d\n", sizeof(a));
printf("size of B: %d\n", sizeof(b));
printf("size of C: %d\n", sizeof(c));
}
我们发现这三种情况类的大小都是1,对于编译器而言,只是给了一个占位符。
this指针
在学习c++的类或者结构体的时候,我们发现存在一个this指针,可以通过this指针来访问类对象中的成员以及函数,那么this指针到底是什么呢?
- this指针是编译器生成的,放在寄存器里面的。调用类成员函数的时候会把this指针传入到函数中去。因此成员函数中可以通过this指针操作类成员
- this指针本质上是结构体或者类的首地址。
- this指针不在类里面,不占用类的大小。
- this指针不能++,不能–,不能重新赋值。
构造函数
构造函数是编译器帮我们自动调用的,在生成新的类对象的时候。
构造函数作用:
- 初始化类的成员
构造函数特点:
- 编译器自动生成无参构造
- 构造函数可以重载
- 构造函数名字和类名一样
- 构造函数无返回值
析构函数
析构函数是编译器帮我们自动调用的,在类销毁的时候。
析构函数的作用
- 释放资源(打开的文件,内存)
RAII
RAII 是c++管理资源的方式,是依赖构造函数和析构函数来实现的。
继承的本质
继承的本质是数据的拷贝。
我们都知道 子类继承父类,生成子类对象的时候,编译器会帮我们调用父类的构造函数来生成父类,实际上编译器帮我们做的事情是把父类的数据拷贝到子类数据存放的前面,并且生成this指针。
实际上子类的成员和父类的成员是放在一起的,因此在子类中都可以通过this指针偏移来访问到。
我们都知道子类对象付给父类指针的时候,父类没办法访问到子类的成员,但是由于数据是排列在一起的原因,我们可以欺骗编译器访问到数据
这个是不安全的,只是想证明子类继承父类,那么子类对象的数据和父类对象的数据其实是放在一起的。