导图社区 类的学习
这是一篇关于类的思维导图,主要内容包括:类和对象,对象的初始化和清理,对象模型和this指针,友元,运算符重载,继承,多态。
编辑于2026-01-09 18:58:09这是一篇关于STL常用容器的思维导图,介绍了C++标准模板库(STL)中的多种容器类型及其相关操作和特性。主要内容包括:String容器,vector容器,deque容器,stack容器,queue容器,list容器,set/multiset容器。
这是一篇关于模板(泛型编程)的思维导图,主要内容包括:概念,函数模板,类模板。模板是建立通用的模具,旨在大大提高代码复用性,但它不可直接使用,只是一个框架,其通用并非万能。
这是一篇关于类的思维导图,主要内容包括:类和对象,对象的初始化和清理,对象模型和this指针,友元,运算符重载,继承,多态。
社区模板帮助中心,点此进入>>
这是一篇关于STL常用容器的思维导图,介绍了C++标准模板库(STL)中的多种容器类型及其相关操作和特性。主要内容包括:String容器,vector容器,deque容器,stack容器,queue容器,list容器,set/multiset容器。
这是一篇关于模板(泛型编程)的思维导图,主要内容包括:概念,函数模板,类模板。模板是建立通用的模具,旨在大大提高代码复用性,但它不可直接使用,只是一个框架,其通用并非万能。
这是一篇关于类的思维导图,主要内容包括:类和对象,对象的初始化和清理,对象模型和this指针,友元,运算符重载,继承,多态。
类
类和对象
struct和class的区别
struct默认权限为公共
class默认权限为私有
对象的初始化和清理
构造函数和析构函数
构造函数的分类以及调用
两种分类方式
按参数分:有参构造和无参构造
按类型分:普通构造和拷贝构造
三种调用方式
括号法
显示法
隐式转换法
拷贝构造函数调用时机
1 使用一个已经创建完成的对象来初始化一个新对象
2 值传递的方式给函数参数传值
3 以值方式返回局部对象
构造函数的调用规则
一般情况下,编译器给至少给一个类添加三个函数
默认构造函数(无参,函数体为空)
默认析构函数(无参,函数体为空)
默认拷贝构造函数,对属性进行值拷贝
构造函数默认规则如下
深拷贝与浅拷贝
浅拷贝:简单的赋值拷贝操作
如果利用编译器提供的拷贝构造函数,会做浅拷贝操作:浅拷贝带来的问题就是堆区的内存重复释放
深拷贝:在堆区重新申请空间,进行拷贝工作
如果用户定义有参构造函数,编译器不再提供默认无参构造,但会提供默认拷贝构造
如果有属性在堆区开辟的,一定要自己提供拷贝构造函数,防止浅拷贝带来的问题
初始化列表
Paerson(int a,int b,int c):MA(a),MB(b),MC(c)
类对象作为类成员
类的成员可以是一个类的对象,称该成员为对象成员
当其他类对象作为本类成员,构造时候先构造类对象,再构造自身,析构的顺序与构造相反
静态成员
静态成员就是在成员对象和成员函数前加static关键字,称为静态成员
静态成员分为
静态成员变量
所有对象共享同一份数据
两种访问方式
通过对象
通过类名
(私有权限访问不到)
在编译阶段分配内存
类内声明,类外初始化
静态成员函数
所有对象共享同一份函数
两种访问方式
通过对象
通过类名
(私有权限访问不到)
静态成员函数只能访问静态成员变量
不可访问非静态成员变量(无法区分到底是哪个对象的变量)
对象模型和this指针
成员变量和成员函数分开储存(只有非静态成员变量才属于类的对象上)
空对象占用内存为1
编译器给每个空对象也分配一个字节空间,是为了区分空对象占内存的位置(非空对象占用内存数为不计入这个1的总空间)
子主题
this指针
this指针指向被调用的成员函数所属的对象(解决非静态成员函数只会诞生一份函数实例,这一块代码如何区分那个哪象调用自己 的问题)
用途
当形参和成员对象同名时,可用this指针来区分
在类的非静态成员函数中返回对象本身,可用 return *this
空指针访问成员函数
if(this==NULL) return ; 防止崩溃
const修饰成员函数
常函数
成员函数后加const后我们称这个函数为常函数
修饰的是this指向,让指针指向的值也不可修改
常函数内不可以修改成员属性
成员属性声明时加关键字mutable后,在常函数中依然可以修改
常对象
声明对象前加const称该对象为常对象
常对象只调用常函数
否则会间接修改属性
友元
三种实现(关键字friend)
全局函数做友元
在类中声明:加关键字friend
类做友元
类中访问另一个类的私有成员,在另一个类加friend class **
成员函数做友元
子主题
运算符重载
加号运算符重载
用编译器提供的通用函数名operator+ 再return temp 调用可简化为person p3=p1+p2;
通过成员函数重载(传一个参数)
通过全局函数重载(传两个参数)
左移运算符
通常只用全局函数重载左移运算符(不用成员函数:无法实现cout在左侧)
传入ostream&cout Person&p
如果要继续输出endl,需要将返回值改为ostream&
递增运算符重载
前置重载++运算符
返回引用的目的是为了一直对同一个数进行递增操作
重载后置++运算符
传参数int代表占位参数,可以用于区分前置和后置(一定要返回值而不是引用:否则返回后储存的局部对象被释放)
先记录当时结果,再递增,再返回当时结果
赋值运算符重载
编译器除了提供的三种类函数还会提供 赋值运算符operator=,对属性进行值拷贝(如果类中有属性指向堆区,做赋值操作时也会出现深浅拷贝问题
先判断是否有属性在堆区,如果有,先释放干净,然后再深拷贝
要连等需要返回自身return*this
关系运算符重载
子主题
函数调用运算符重载
函数调用运算符()也可以重载
匿名函数对象
由于重载后使用方式非常像函数的调用,因此称为仿函数
仿函数没有固定写法,非常灵活
继承
基本语法
class 子类(派生类) :public 父类(基类)
继承方式
公共继承
子类访问不到private,其余不变
保护继承
子类访问不到private,其余变为保护权限
子类访问不到private,其余不变
私有继承
子类访问不到private,其余变为私有权限
继承中的对象模型
父类的所有属性都被继承下来了(虽然许多访问不到)
继承中构造和析构顺序
子类继承父类后,当创建子类对象时,也会调用父类的构造函数
顺序:父子子父
继承同名成员处理方式
当子类与父类出现同名的成员,通过子类对象,访问到子类或父类的同名数据
访问子类同名成员:直接访问
访问父类同名成员:需要加作用域(s.Base::m_a )
继承同名静态成员处理方式
处理方式一致
访问子类同名成员:直接访问
访问父类成员:需要加作用域
多继承语法
允许一个类继承多个类
语法:calss 子类 :继承方式 父类1 ,继承方式 父类2
多继承可能会引发父类中有同名成员出现,需要加作用域以区分
菱形继承
两个派生类继承同一个基类又有某个类同时继承两个派生类
带来的问题是子类继承两份相同的数据,导致资源浪费以及毫无意义
利用虚继承可以解决菱形继承问题
多态
基本概念
静态多态
函数重载和运算符重载属于静态多态,复用函数名
函数地址早绑定--编译阶段确定函数地址
动态多态
派生类和虚函数实现运行时多态
函数地址晚绑定--运行阶段确定函数地址
父类和子类不需要转换
满足条件
有继承关系
父类加vritual,子类重写父类的虚函数(重写:函数返回值类型 函数名 参数列表 完全一致称为重写
使用条件
父类指针或引用指向子类对象
多态原理剖析
父类虚函数4字节,因为有虚函数指针(原先是1,因为只包含一个非静态函数(不在类中储存))
纯虚函数和抽象类
多态中,通常父类虚函数无意义,因此改为纯虚函数
纯虚函数语法:virtual 返回值类型 函数名 (参数列表)=0
当类中有了纯虚函数,这个类也称为 抽象类
抽象类特点
无法实例化对象
子函数必须重写抽象类中的纯虚函数,否则也属于抽象类
虚析构和纯虚析构
多态使用时,如果子类中有属性开辟到堆区,那么父类指针在使用时无法调用到子类的析构代码
解决方式:将父类中的析构函数改为虚析构或者纯虚析构
虚析构和纯虚析构共性
可以解决父类指针释放子类对象
都需要具体的函数实现
虚析构与纯虚析构区别
如果是纯虚析构,该类属于抽象类无法实例化对象