22.this指针
1.this指针工作原理
我们知道,c++的数据和操作也是分开存储,并且每一个非内联成员函数(non-inline member function)只会诞生一份函数实例,也就是说多个同类型的对象会共用一块代码
那么问题是:这一块代码是如何区分那个对象调用自己的呢?

c++通过提供特殊的对象指针,this指针,解决上述问题。This指针指向被调用的成员函数所属的对象。
c++规定,this指针是隐含在对象成员函数内的一种指针。当一个对象被创建后,它的每一个成员函数都含有一个系统自动生成的隐含指针this,用以保存这个对象的地址,也就是说虽然我们没有写上this指针,编译器在编译的时候也是会加上的。因此this也称为“指向本对象的指针”,this指针并不是对象的一部分,不会影响sizeof(对象)的结果。
this指针是C++实现封装的一种机制,它将对象和该对象调用的成员函数连接在一起,在外部看来,每一个对象都拥有自己的函数成员。一般情况下,并不写this,而是让系统进行默认设置。
this指针永远指向当前对象。
this指针永远指向当前对象。
成员函数通过this指针即可知道操作的是那个对象的数据。This指针是一种隐含指针,它隐含于每个类的非静态成员函数中。This指针无需定义,直接使用即可。
注意:静态成员函数内部没有this指针,静态成员函数不能操作非静态成员变量。
2.this指针的使用
●当形参和成员变量同名时,可用this指针来区分
●在类的非静态成员函数中返回对象本身,可使用return *this.
class Person{
public:
	//1. 当形参名和成员变量名一样时,this指针可用来区分
	Person(string name,int age){
//name = name;
		//age = age; //输出错误
		this->name = name;
		this->age = age;
	}
	//2. 返回对象本身的引用
	//重载赋值操作符
	//其实也是两个参数,其中隐藏了一个this指针
	Person PersonPlusPerson(Person& person){
		string newname = this->name + person.name;
		int newage = this->age + person.age;
		Person newperson(newname, newage);
		return newperson;
	}
	void ShowPerson(){
		cout << "Name:" << name << " Age:" << age << endl;
	}
public:
	string name;
	int age;
};
//3. 成员函数和全局函数(Perosn对象相加)
Person PersonPlusPerson(Person& p1,Person& p2){
	string newname = p1.name + p2.name;
	int newage = p1.age + p2.age;
	Person newperson(newname,newage);
	return newperson;
}
int main(){
	Person person("John",100);
	person.ShowPerson();
	cout << "---------" << endl;
	Person person1("John",20);
	Person person2("001", 10);
	//1.全局函数实现两个对象相加
	Person person3 = PersonPlusPerson(person1, person2);
	person1.ShowPerson();
	person2.ShowPerson();
	person3.ShowPerson();
	//2. 成员函数实现两个对象相加
	Person person4 = person1.PersonPlusPerson(person2);
	person4.ShowPerson();
	system("pause");
	return EXIT_SUCCESS;
}
3.视频内容

程序1:
#pragma warning(disable:4996)
//2022年9月22日20:31:02
#include <iostream>
using namespace std;
class Maker
{
public:
    Maker()
    {
        a = 10;
        b = 20;
    }
    void func()
    {
        cout << this->a << " " << this->b << endl;
    }
public:
    int a;
    int b;
};
void test01()
{
    //1.分配空间。2.调用构造函数
    Maker m;
    m.func();
}
int main()
{
    test01();
    system("pause");
    return 0;
}
输出结果:
10 20
请按任意键继续. . .
程序2:
#pragma warning(disable:4996)
//2022年9月22日20:31:02
#include <iostream>
using namespace std;
class Maker
{
public:
    Maker()
    {
        a = 10;
        b = 20;
    }
    void func()//func()函数只有一份
    {
        cout << this->a << " " << this->b << endl;
    }
public:
    int a;
    int b;
};
void test01()
{
    //1.分配空间。2.调用构造函数
    Maker m;
    m.func();
    Maker m2;
    m2.func();
}
class Maker2
{
public:
    int id;
public:
    //1.当形参名和成员变量名相同时,用this指针区分
    Maker2(int id)
    {
        this->id = id;
    }
    //2.反回对象的本身
    Maker2 &getMaker2()
    {
        return *this;//运算符重载时有用
    }
};
int main()
{
    test01();
    system("pause");
    return 0;
}
程序3:
#pragma warning(disable:4996)
//2022年9月22日20:31:02
#include <iostream>
using namespace std;
class Maker
{
public:
    Maker()
    {
        a = 10;
        b = 20;
    }
    void func()//func()函数只有一份
    {
        cout << this->a << " " << this->b << endl;
    }
public:
    int a;
    int b;
};
void test01()
{
    //1.分配空间。2.调用构造函数
    Maker m;
    m.func();
    Maker m2;
    m2.func();
}
class Maker2
{
public:
    int id;
    static int a;//静态成员变量
public:
    //1.当形参名和成员变量名相同时,用this指针区分
    Maker2(int id)
    {
        this->id = id;
    }
    //2.反回对象的本身
    Maker2 &getMaker2()
    {
        return *this;//运算符重载时有用
    }
    static void func()
    {
        this->a = 300;//静态成员变量,指针指向的空间并没有a
    }
};
int Maker2::a = 200;
int main()
{
    test01();
    system("pause");
    return 0;
}
4.this指针(重点难点)
1.每个对象都有一个隐藏的this指针,但不属于对象,是编译器添加的
2.编译器会把this指针传入成员函数内
3.this指针指向对象的存储空间
4.this的作用:
class Maker2
{
public:
	//1.当形参名和成员变量名相同时,用this指针区分
	Maker2(int id)
	{
		this->id = id;
	}
	//2.返回对象的本身
	Maker2 &getMaker2()
	{
		return *this;//运算符重载时有用
	}
public:
	int id;
};
5.拓展
1.this指针指向的空间有没有存储静态成员变量?
没有
2.this指针的指向可以改变吗?
this指针的指向不能改变,也就是说this是Maker *const this;
6.防止空指针调用成员函数
class Maker
{
public:
	Maker()
	{
		a = 20;
	}
	void printMaker()
	{
		if (this == NULL)
		{
			cout << "this==NULL" << endl;
			return;
		}
		cout << this->a << endl;
	}
private:
	int a;
};
void test()
{
	Maker *m = NULL;
	m->printMaker();
}
												
											22.this指针的更多相关文章
- C++:向函数传递对象(对象、对象指针、对象引用)
		
3.5.1 使用对象作为函数参数,其方法与传递基本类型的变量相同 //例3.21 使用对象作为函数参数 #include<iostream> using namespace std; ...
 - c/c++ 函数指针的用法
		
[目录] 基本定义 c 函数指针使用举例 c++ 函数指针使用举例 函数指针作为函数参数 函数指针作为函数返回值 函数指针数组 typedef 简化函数指针操作 c语言函数指针的定义形式:返回类型 ( ...
 - C语言关于指针函数与函数指针个人理解
		
1,函数指针 顾名思义,即指向函数的指针,功能与其他指针相同,该指针变量保存的是所指向函数的地址. 假如是void类型函数指针定义方式可以是 void (*f)(参数列表);亦可以先用 typedef ...
 - C语言查缺补漏
		
7.用ucontext实现简单的用户空间协作多线程 转 http://blog.chinaunix.net/uid-26000137-id-3973004.html http://blog.csdn. ...
 - Redis内存管理(二)
		
上一遍详细的写明了Redis为内存管理所做的初始化工作,这篇文章写具体的函数实现. 1.zmalloc_size,返回内存池大小函数,因为库不同,所以这个函数在内部有很多的宏定义,通过具体使用的库来确 ...
 - 使用struct实现面向对象编程的封装
		
虽然C是面向过程的语言,但是这不代表C不能使用面向对象的思想,本质上说语言只是一种手段而已,一种外在的表现形式,支持面向对象的语言只是通过设计的特定的关键字更好的表现了面向对象编程而已.C中也可以使用 ...
 - OC基础11:基本的C语言特性2
		
"OC基础"这个分类的文章是我在自学Stephen G.Kochan的<Objective-C程序设计第6版>过程中的笔记. 19.定义一个int类型的指针: int ...
 - the c programing language 学习过程5
		
lumped 集成总结 mandating托管 consecutively连续地 contiguous临近的 mnemonic记忆力的 mimics 酷似 魔方 bind捆绑 synonym同义词 s ...
 - C语言完美体系
		
**第 1 篇 C 语言第一阶段 13 1.1C 语言第一阶段--语言课程概述 13 1.1.1 什么是语言,什么是 C 语言 13 1.1.2 基本常识 14 1.1.3 人与计算机之间的更好的交互 ...
 - 滴水逆向初级-C语言(二)
		
2.1.C语言的汇编表示 c语言代码 int plus(int x,int y) { return 0; } void main() { __asm { mov eax,eax } //调用函数 pl ...
 
随机推荐
- postman导出Collection文件
			
postman接口调用工具可以将曾经使用过的请求配置导出为文件保存,方法如下: 1.编写一个接口测试用例 2.按组分类 3.导出 参考来源: https://blog.csdn.net/IBLiplu ...
 - Redis基础命令和持久化
			
Redis命令工具 Redis-server :用于启动Redis的工具 Redis-benchmark:用于检查Redis在本机的运行效率 Redis-check-aof:修复aof持久化文件 Re ...
 - noi 1.5 36 计算多项式的值
			
描述 假定多项式的形式为xn+xn-1+-+x2+x+1,请计算给定单精度浮点数x和正整数n值的情况下这个多项式的值. 输入 输入仅一行,包括x和n,用单个空格隔开.x在float范围内,n < ...
 - 第三讲: xpath定位方法
			
 如果大家有机会做web自动化测试的工作,在框架搭建好之后,大部分的工作都是在写定位表达式,然而,8大元素定位方法中,id.name.class_name.link_text.partial_lin ...
 - mysql循环插入分隔符分开的字符串
			
CREATE DEFINER=`root`@`localhost` PROCEDURE `test`()BEGIN DECLARE i,help_topic_id INT; SET i=10469; ...
 - 音速启动 Vstart 5.7  win10手动移除后台设置主页
			
Vstart 用了快12年了,用Wireshark跟踪确实会访问广告页面,也会去上传数据.还会悄悄设置主页 ,所以在Win10上老是被干掉 也想着换 CLaunch 确实不喜欢. Rolan 买了一年 ...
 - Spring-IoC中Set和构造器注入
			
新建Maven工程 修改pom文件 1 <?xml version="1.0" encoding="UTF-8"?> 2 <project x ...
 - vue3.0+vite按需引入element plus
			
1.安装vite-plugin-style-import yarn add vite-plugin-style-import -D 2.在项目根目录下的vite.config.js中配置 import ...
 - pytorch 创建图与叶子节点与根节点
			
创建时用户直接给出的为叶子节点,没有fn 由几个叶子节点推导来的为最终结果,为root节点,有fn. 譬如: x=tt.tensor([1],dtype='flaot',requires_grad=T ...
 - LOJ数列分块入门九题(上)
			
一转眼,已经有整整一年没有在博客园写博客了.去洛谷写了几篇(How time flys. 最近突然想起其实我不太擅长分块算法,又想起去年暑假有位同学同我提起过LOJ的数列分块九题,说来惭愧,打了这么久 ...