这篇博文如题
this关键字是一个指针,也同时是一个const指针,它指向正在使用的对象,通过它可以访问当前对象的所有成员。
从本质而言,this实际上是成员函数的一个形参,在调用成员函数时将对象的地址作为实参传递给this,只不过这是隐式的由编译器自动添加的。
this作为隐式形参,本质是成员函数的局部变量,所以只能用在成员函数的内部,并且只有在通过对象调用成员函数时才给this赋值
this 是const指针,它的值是不能被修改的。
this只能在成员函数内部使用,只有当对象被创建后this才有意义,因此不能再静态成员函数中使用。
我知道,肯定是一脸闷逼
我来举个栗子
假设你是一个快递员(成员函数),每天要给无数个客户(对象)送快递(操作数据)。每个客户都有一个专属的地址标签(this
指针),贴在快递箱上。你的工作流程是:
客户喊你送货: 客户A.送货();
→ 客户A把自己的地址标签(&客户A
)偷偷塞给你。
你按标签找到客户的家: 你根据标签找到客户A的家(this->
),然后操作他的快递(数据)。
避免送错: 如果没有这个标签,你可能把客户B的快递送到客户A家!this
就是为了明确当前操作的是哪个对象。
为什么静态函数没有 this
?
静态函数属于类,不依赖具体对象。
就像「快递公司的总部客服」,不需要知道具体客户的地址,只处理全局事务。
来段代码验证一下
#include
using namespace std;
class Student
{
public:
Student(string names, int ages)
{
this->name = names;//分别进行赋值
this->age = ages;
}
void show()
{
cout << "this" << this << endl;
}
string name;
int age;
};
int main()
{
Student s1 = { "zc",20 };
s1.show();
cout << "s1->" << &s1 << endl;
Student s2 = { "ww",22 };
s2.show();
cout << "s2->" << &s2 << endl;
//可以看到位置相同
return 0;
}
用我们学过的知识判断一个图形是否为正方形,并算出它的面积
答案如下
class Rect
{
private:
double wight, height;
public:
//进行赋值
Rect(double wights, double heights)
{
this->wight = wights;
this->height = heights;
return;
}
//判断是否为正方形
bool is_square()
{
return this->wight == this->height;
}
//输出矩阵面积
void area()
{
cout << this->height * this->wight << endl;
}
};
int main()
{
Rect a1(100,200);
bool b = a1.is_square();
if (b)
cout << "是正方型" << endl;
else
cout << "不是正方型" << endl;
a1.area();
return 0;
}
c++中所有的 成员变量 和成员函数 都有访问权限,本质上就是能不能访问该类中的成员变量和成员函数。
c++中,用来控制访问权限的关键字有 public,protected,private,他们分别表示,公有的,受保护的和私有的,它们被统称为成员访问限定符。
我来一一介绍一下
作用:标记为 public
的成员,谁都可以访问,就像公共场所。
例子:类的功能接口(比如开关灯的按钮),外部代码可以直接调用。
类比:你家的大门钥匙,所有人都能用它开门。
作用:标记为 private
的成员,只能被类自己访问,外部代码和子类都看不到。
例子:类的内部数据(比如灯泡的电压),只能通过类提供的 public
方法间接修改。
类比:你的日记本,只有你自己能看,别人不能直接翻。
作用:标记为 protected
的成员,类自己和它的子类能访问,但外部代码不能。
例子:父类想让子类继承某些数据,但又不对外公开。
类比:家族传家宝,自家人(子类)可以用,外人不能碰。
放入代码中看看
class Student
{
public:
int v1 = 100;
protected:
int v2 = 200;
private:
int v3 = 300;
public:
void prientInfo()
{
cout << "v1=" << v1 << endl;
cout << "v2=" << v2 << endl;
cout << "v3=" << v3 << endl;
}
};
int main()
{
Student s1;
s1.prientInfo();
s1.v1 = 999;
s1.prientInfo();
//s1.v2 = 888;//对象不能访问受保护的成员变量
//s1.v3=777;//对象不能访问私有的成员变量
return 0;
}
类的友元函数可以访问到类的私有成员和保护成员。
友元函数在类中定义,但是类的友元函数并不是成员函数。
定义友元函数要使用friend关键字
简单的举个栗子
你的钱包(类)里藏了钱(private,protected
),但你的好朋友「查余额函数」可以随时看你有多少钱。
来段代码
class Student {
public:
Student(string name, int age)
{
this->names = name;
this->ages = age;
}
private:
string names;
int ages;
};
void printName(Student s1)
{
cout << s1.names << endl;//报错,因为names是私人的
}
int main()
{
Student s1("zc", 32);
printName(s1);
return 0;
}
如果我们把它改成友元函数就不会报错
class Student {
public:
Student(string name, int age)
{
this->names = name;
this->ages = age;
}
friend void printName(Student s1);//不报错,因为是友元函数
private:
string names;
int ages;
};
void printName(Student s1)
{
cout << s1.names << endl;
}
int main()
{
Student s1("zc", 32);
printName(s1);
return 0;
}
在c++中,可以将一个类声明为友元类,如果一个类是另一个类的友元类,友元类可以访问类的所有私有成员。
简单点说
你家里有个保险箱,只有你自己能打开。但如果你信任某个好朋友,你可以告诉他密码,这样他也能打开你的保险箱。
在C++中,友元类就是这个“好朋友”——它被允许访问另一个类的“隐私”(比如私有成员变量和函数)。
假设有两个类关系非常紧密,比如:
汽车类(Car) 和 引擎类(Engine)
学生类(Student) 和 成绩单类(ReportCard)
如果引擎需要直接操作汽车的内部零件,或者成绩单需要直接修改学生的成绩,这时就可以用友元类,让它们能直接访问对方的“隐私”。
来点代码
class Teacher;//需要使用需要提前声明
class Student {
private:
string name;
int age;
public:
Student(string names, int ages)
{
this->name = names;
this->age = ages;
}
void stu_preat(Teacher& t);//使用了引用的方法
};
class Teacher {
private:
string name;
int age;
public:
Teacher(string names, int ages)
{
this->name = names;
this->age = ages;
}
friend class Student;//友元类
};
void Student::stu_preat(Teacher& t)//可以访问私有的数据
{
cout << this->name << endl;
cout << t.name << endl;
}
int main()
{
Student s1("zhans", 22);
Teacher s2("leiss",23);
s1.stu_preat(s2);
return 0;
}
需要注意的是
单向关系:如果Teacher
把Student
当朋友,Stuendt
能访问Teacher
的隐私,但反过来不行!除非Stuendt
也声明Teacher
是朋友。
慎用:友元类会破坏“封装性”(面向对象的基本原则),滥用会导致代码难以维护。