-
this指针
1)类中的成员函数(包括构造函数、析构函数)中都隐藏一个该类类型指针参数,名为this;在成员函数中访问类中的其它成员,其本质都是this来实现的。
2)对于普通成员函数,this指向调用对象的地址;如果对于构造函数,this指向正在创建的对象地址。
3)大多数情况可以忽略this,在成员函数宏直接访问类中的其它成员,但是以下几个特殊场景必须要使用this指针:
–》区分作用域#include <iostream> using namespace std; class Teacher{ public: /* Teacher(const string&name,int age,double sal) :m_name(name),m_age(age),m_sal(sal){ cout << "构造函数:" << this << endl; }*/ //当参数变量和成员变量名字相同时,可以通过 //this区分,通过this所访问到的一定是成员变量 Teacher(const string& m_name,int m_age, double m_sal){ this->m_name = m_name; this->m_age = m_age; this->m_sal = m_sal; } void print(void){ cout << m_name << "," << m_age << "," << m_sal << endl; cout << this->m_name << ","<< this->m_age << "," << this->m_sal << endl; }/*编译器处理后: void print(Teacher* this){ cout << this->m_name << ","<< this->m_age << "," << this->m_sal << endl; }*/ private: string m_name; int m_age; double m_sal; }; int main(void){ Teacher t1("张三",45,8000); Teacher t2("李四",46,9000); t1.print();//Teacher::print(&t1) t2.print();//Teacher::print(&t2) cout << "&t1=" << &t1 << endl; cout << "&t2=" << &t2 << endl; return 0; }
–》从成员函数返回调用对象自身(返回自引用)#include <iostream> using namespace std; class Counter{ public: Counter(int count=0):m_count(count){} Counter& add(void){ ++m_count; //this指向调用对象,*this就是调用对象自身 return *this;//返回自引用 } void print(void){ cout << "计数值:" << m_count << endl; } private: int m_count; }; int main(void){ Counter c; c.add().add().add(); c.print();//3 return 0; }
注:上述代码中,add函数返回一定要是引用,如果返回不是引用而是对象则下:
c.add().add().add()
的调用过程为,c先调用一次add(),然后add代码中执行到return *this时,发生拷贝构造,将新复制出来的对象返回,然后新复制出来的对象调用这个第二个add(),同理,第二个add()在返回时,先将要返回的对象拷贝,然后返回这个新拷贝出来的对象,然后这个对象再执行第3个add(),所以,总的来说就是,有3个对象分别执行了一个一次add,3个对象中的m_count值分别为1,2,3,在返回对象而不是引用的情况下,增加如下代码验证第3个是3Counter c2 = c.add().add().add(); c2.print();
会发现成c2的打印结果为3
–》从类的内部销毁对象自身(对象自销毁)delete this
;
–》作为成员函数的实参,实现不同对象之间的交互#include <iostream> using namespace std; class Student;//短视声明 class Teacher{ public: void educate(Student* s); void reply(const string& answer); private: string m_answer; }; class Student{ public: void ask(const string& q,Teacher* t); }; void Teacher::educate(Student* s){ //通过this指针,将教师对象地址传给学生对象 s->ask("什么是this指针?",this);//1) cout << "学生回答:" << m_answer << endl;//5) } void Teacher::reply(const string& answer){ m_answer = answer;//4) } void Student::ask(const string& q,Teacher* t){ cout << "问题:" << q << endl;//2) t->reply("this就是指向调用对象的地址");//3) } int main(void){ Teacher t; Student s; t.educate(&s); return 0; }
-
常成员函数
1)在一个成员函数参数表的后面加const,这个成员函数就是常成员函数(常函数).
返回类型 函数名(形参表) const {函数体}
2)常成员函数中this指针是一个常指针,不能在常成员函数中直接修改成员变量的值。
注:可以在常成员函数中强转this来修改成员或者被mutable修饰的成员变量,可以在常成员函数直接修改
3)非常对象既可以调用非常函数也可以调用常函数;但是常对象只能调用常函数,不能调用非常函数
注:常对象也包括常指针和常引用#include <iostream> using namespace std; class A{ public: //void func1(const A* this) void func1(void) const { cout << "常函数" << endl; //func2();//this->func2() } //void func2(A* this) void func2(void){ cout << "非常函数" << endl; } }; int main(void){ A a; a.func1();//A::func1(&a),A* a.func2();//A::func2(&a),A* const A a2 = a; a2.func1();//A::func1(&a2),const A* //a2.func2();//A::func2(&a2),const A* const A* pa = &a;//pa:常指针 pa->func1(); //pa->func2(); const A& ra = a;//ra:常引用 ra.func1(); //ra.func2(); return 0; }
4)同一个类中,函数名和参数表相同的成员函数,其常版本和非常版本可以构成有效的重载关系;常对象匹配常版本,非常对象匹配非常版本。
#include <iostream> using namespace std; class A{ public: void func(void)const{ cout << "func常版本" << endl; } void func(void){ cout << "func非常版本" << endl; } }; int main(void){ A a; a.func();//非常版本 const A a2 = a; a2.func();//常版本 return 0; }
C++学习之this指针和常成员函数
最新推荐文章于 2023-02-12 21:09:11 发布