C++语法学习(15)
一、this指针
对于成员函数,this指针就指向调用该函数的对象。
对于构造函数,this指针就指向这个正在被构造的对象。
1.区分成员变量
2.在类的内部访问调用对象自身。
交叉类问题
class A{
B m_b;//ERROR
//B* m_b;//OK
};
class B{
A m_a;//ERROR
//A* m_a;//OK
};
sizeof(A) = ?,所以不是交叉类,直接是错误的。无法算出类的大小。
3.从成员函数中返回调用对象自身,函数调用连用。
二、常对象与常函数
1.常对象
2.常函数
在一个成员函数的参数表后面加上const,这个成员函数就成为常函数。
class A{
void foo (int a) const {...}
};
这样的成员函数的this指针是常指针。
在这样的成员函数中无法修改成员变量的值。防止在成员函数内部意外地修改成员变量。
通过常对象只能调用常函数。
原型相同的常函数和非常函数可以构成重载。非常对象调用非常版本,常对象调用常版本。如果
没有非常版本,则非常对象也能调用常版本。
三、析构函数
1.语法
class 类名{
~类名(void){...}
};
2.当对象被销毁时,该对象所属类型的析构函数被自动执行,于中可以释放构造时分配的资源。
局部变量形式的对象离开其作用域时被销毁。
全局变量或静态局部变量形式的对象在进程结束时被销毁。
成员变量形式的对象在其拥有者对象被销毁时被销毁。
通过new动态分配的对象,在delete时被销毁。
3.构造和析构的顺序
构造函数:构造基类部分 -> 构造成员变量 -> 执行构造代码
析构函数:执行析构代码 -> 析构成员变量 -> 析构基类部分
4.如果一个类中没有定义析构函数,那么系统就会提供一个缺省的析构函数,但是该函数不会释放动态分配的资源。
5.析构函数不能重载,因为析构函数不能有任何参数。
四、拷贝构造函数和拷贝赋值运算符
1.拷贝构造:构造一个已有对象的副本
Student s1("张飞", 28);
Student s2 (s1);//拷贝构造
Student s3 = s2;//拷贝构造
2.一般情况下,对象可以直接拷贝构造,因为系统会提供一个默认的拷贝构造函数:
Student::Student(const Student& that){...}
其工作,对于基本类型的成员变量,按字节复制,对于类类型的成员变量,调用相应类型的拷贝构造函数。
浅拷贝:

深拷贝:

3.为了解决浅拷贝的问题,往往需要自己定义一个支持对象间深拷贝的拷贝构造函数。
4.拷贝赋值
Student s1("张飞", 28);
Student s2("赵云", 22);
s2 = s1;//拷贝赋值
5.缺省方式的拷贝赋值只能做浅拷贝,欲实现对象间的深拷贝,需要自己定义拷贝赋值运算符函数。
Student& operator= (const Student& that);
int a=10,b=20,c=30;
a = b = c;//都是30
五、静态成员
非静态成员是属于对象的,而静态成员是属于类的。
1.静态成员变量
1)需要在类的外部单独定义并初始化;
2)可以通过类直接访问,也可以通过对象访问;
3)在该类的多个对象实例间共享;
4)和普通成员变量一样也受访控属性的约束。
构造函数不去定义静态成员变量。在类的外部单独定义和初始化。(疑问:静态变量是否是类大小一部分?)
静态的成员变量只有一份,在对象间共享。
2.静态成员函数
1)可以通过类直接访问,也可以通过对象访问;
2)和普通成员函数一样也受访控属性的约束。
3)在静态成员函数只能访问静态成员,而在非静态成员函数中既可以访问非静态成员,也可以访问静态成员;
4)静态成员函数没有this指针,也没有const属性。
浙公网安备 33010602011771号