每一个非静态成员函数只会诞生一份函数实例,也就是说多个同类型的对象会共用一块代码那么问题是:这—块代码是如何区分那个对象调用自己的呢?
C++通过提供特殊的对象指针,this指针,解决上述问题。this指针指向被调用的成员函数所属的对象
this指针是隐含每一个非静态成员函数内的—种指针
this指针不需要定义,直接使用即可
this指针的用途:
- 当形参和成员变量同名时,可用this指针来区分
- 在类的非静态成员函数中返回对象本身,可使用return this
一、this指针
1 this指针解决名称冲突
#include <iostream> using namespace std; class Person { public: Person(int age) { age = age; } int age; }; //1 解决名称冲突 void test1() { Person p1(18); cout << "p1的年龄为=" << p1.age << endl; } int main() { test1(); return 0; }
输出年龄乱码
分析
光标放在形参age上,发现三个age 都是灰色,系统认为这个三个age 是同一数据
解决1:
将成员变量和形参书写是上加m_区分
class Person { public: Person(int age) { m_Age = age; } int m_Age; };
解决2:
this指针指向 被调用的成员函数 所属对象
class Person { public: //1 解决名称冲突 Person(int age) { //this指针指向 被调用的成员函数 所属对象 this->age = age; } int age; };
2 返回对象本身用*this
class Person { public: //1 解决名称冲突 Person(int age) { //this指针指向 被调用的成员函数 所属对象 this->age = age; } //2 返回对象本身用*this void PersonAddAge(Person &p) { this->age += p.age; } int age; }; //1 解决名称冲突 void test1() { Person p1(18); cout << "p1的年龄为=" << p1.age << endl; //2 返回对象本身用*this Person p2(10); p2.PersonAddAge(p1); cout << "p2的年龄为=" << p2.age << endl; }
现在想要年龄后面继续累加,出错
函数test1()是void无返回值型,调用完毕就不能再调用了
p2.PersonAddAge(p1).PersonAddAge(p1).PersonAddAge(p1);
如果每次调用完毕,可以返回到p2,就可以继续再调用PersonAddAge(p1);
//2 返回对象本身用*this Person &PersonAddAge(Person &p) { //this指向p2的指针,而*this指向的就是p2这个对象的本体 this->age += p.age; return *this; }
完整代码
#include <iostream> #include<string> using namespace std; //1 解决名称冲突 //2 返回对象本身用*this class Person { public: //1 解决名称冲突 Person(int age) { //this指针指向 被调用的成员函数 所属对象 this->age = age; } //2 返回对象本身用*this Person &PersonAddAge(Person &p) { //this指向p2的指针,而*this指向的就是p2这个对象的本体 this->age += p.age; return *this; } int age; }; //1 解决名称冲突 void test1() { Person p1(18); cout << "p1的年龄为=" << p1.age << endl; //2 返回对象本身用*this Person p2(10); p2.PersonAddAge(p1).PersonAddAge(p1).PersonAddAge(p1); cout << "p2的年龄为=" << p2.age << endl; } int main() { test1(); return 0; }
二、空指针调用成员函数
C++中空指针也是可以调用成员函数的,但是也要注意有没有用到this指针
如果用到this指针,需要加以判断保证代码的健壮性
#include<iostream> using namespace std; //空指针调用成员函数 class Person { public: void showClassName() { cout << "This is Person class" << endl; } void showPersonAge() { //报错原因是因为传入的是空指针 cout << "age=" <<m_Age<< endl; } int m_Age; }; void test1() { Person* p = NULL; p->showClassName(); // p->showPersonAge();//报错原因是因为传入的是空指针 } int main() { test1(); return 0; }
//报错原因是因为传入的是空指针
if(this==NULL) return; //解决空指针出错
void showPersonAge() { //报错原因是因为传入的是空指针 if(this==NULL) return; //解决空指针出错 cout << "age=" <<m_Age<< endl; }
完整代码
#include<iostream> using namespace std; //空指针调用成员函数 class Person { public: void showClassName() { cout << "This is Person class" << endl; } void showPersonAge() { //报错原因是因为传入的是空指针 if(this==NULL) return; //解决空指针出错 cout << "age=" <<m_Age<< endl; } int m_Age; }; void test1() { Person* p = NULL; p->showClassName(); p->showPersonAge();//报错原因是因为传入的是空指针 } int main() { test1(); return 0; }
三、const修饰成员函数
常函数:
·成员函数后加const后我们称为这个函数为常函数
.常函数内不可以修改成员属性
·成员属性声明时加关键字mutable后,在常函数中依然可以修改
常对象:
·声明对象前加const称该对象为常对象
·常对象只能调用常函数
解决方法:
成员属性声明时加关键字mutable,在常函数中才可以修改
mutable int m_B;//特殊变量,即使在常函数中,也可修饰这个值,加关键字mutable
//常函数 class Person { public: //this指针的本质是指针常量,指针的指向是不可以修改的 //const Person *const this; //在成员函数后面加const,修饰的是this指向,让指针指向的值也不可以修改 void showPerson() const { // m_A = 100; //常函数内不可以修改成员属性 // this->m_A = 100; // this = NULL; m_B = 100; //成员属性声明时加关键字mutable,在常函数中才可以修改 } int m_A; mutable int m_B;//特殊变量,即使在常函数中,也可修饰这个值,加关键字mutable };
const Person p;//在对象前加const变常对象
//常对象 void test2() { const Person p;//在对象前加const变常对象 // p.m_A = 100;//报错 p.m_B = 100;//m_B是特殊值,在常对象下也可以修改 //常对象只能调用常函数 p.showPerson(); // p.func();//常对象不可以调用普通成员函数,因为普通成员函数可以修改属性 }
完整代码
#include<iostream> using namespace std; //常函数 //常对象 class Person { public: //this指针的本质是指针常量,指针的指向是不可以修改的 //const Person *const this; //在成员函数后面加const,修饰的是this指向,让指针指向的值也不可以修改 void showPerson() const { // m_A = 100; //常函数内不可以修改成员属性 // this->m_A = 100; // this = NULL; m_B = 100; //成员属性声明时加关键字mutable,在常函数中才可以修改 } void func() { } int m_A; mutable int m_B;//特殊变量,即使在常函数中,也可修饰这个值,加关键字mutable }; //常函数 void test1() { Person p; p.showPerson(); } //常对象 void test2() { const Person p;//在对象前加const变常对象 // p.m_A = 100;//报错 p.m_B = 100;//m_B是特殊值,在常对象下也可以修改 //常对象只能调用常函数 p.showPerson(); // p.func();//常对象不可以调用普通成员函数,因为普通成员函数可以修改属性 } int main() { test1(); return 0; }
参考:黑马程序员
哔哩哔哩 黑马程序员
到此这篇关于C++ this指针和空指针的具体使用的文章就介绍到这了,更多相关C++ this指针和空指针内容请搜索自学编程网以前的文章或继续浏览下面的相关文章希望大家以后多多支持自学编程网!
- 本文固定链接: https://www.zxbcw.cn/post/210944/
- 转载请注明:必须在正文中标注并保留原文链接
- QQ群: PHP高手阵营官方总群(344148542)
- QQ群: Yii2.0开发(304864863)