this指针
是只能在非静态成员函数或类型内访问的class、
struct、
union
指针。 它指向为其调用成员函数的对象。 静态成员函数没有 this
指针。我们先来看一个如下这样一个日期类:
class Date
{
public:
void Init(int year, int month, int day)
{
_year = year;
_month = month;
_day = day;
}
void Print()
{
cout << _year << "/" << _month << "/" << _day << endl;
}
private:
int _year;
int _month;
int _day;
};
int main()
{
Date d1, d2;
d1.Init(2022, 8, 8);
d2.Init(2022, 8, 9);
d1.Print();
d2.Print();
return 0;
}
运行结果:
可以看到,d1、d2都被成功初始化了,这里在main函数中实例化出了两个不同的对象,d1、d2,可是在C语言中我们知道要修改一个值时需要传的是这个值的地址,例如要改变int类型的变量就要传这个变量的地址(int*)给int*这么一个形参,要改变指针的指向,指针类型是int*,那么就要传指针的地址(int**)给int**这么一个形参。
然而,在上边程序中我们可以看到在类成员函数Init中并没有区分不同对象的这么一个形参,d1、d2在初始化时调用的都是类成员函数Init,那Init是怎么样知道它是要对d1还是d2进行初始化呢?按照C语言的规则来说,他应该是要传d1、d2的地址才能找到相应对象进行初始化呀。
当然的确如此,确实是要把d1、d2的地址传过去,但C++通过引入this指针隐藏了这一步骤,C++编译器给每个“非静态的成员函数“增加了一个隐藏的指针参数,让该指针指向当前对象(函数运行时调用该函数的对象),在函数体中所有“成员变量”的操作,都是通过该指针去访问。只不过所有的操作对用户是透明的,即用户不需要来传递,编译器自动完成。
实际调用情况:
注(this指针特性):
1. this指针的类型:类类型* const(如上程序中this指针类型就是Date* const),即成员函数中,不能给this指针赋值。
2. 实参和形参位置上不能显示传递this指针。
3. 只能在“成员函数”的内部使用this指针。
4. this指针本质上是“成员函数”的形参,当对象调用成员函数时,将对象地址作为实参传递给this形参,所以对象中不存储this指针,this指针如不进行优化就是存储在栈区上,但编译器可能会进行优化会把this指针存储到寄存器中。
5. this指针是“成员函数”第一个隐含的指针形参,一般情况由编译器通过ecx寄存器自动传递,不需要用户传递 。