240409 类和对象

1 构造函数

1.1 特性补充

  • 无参构造和全缺省参数构造构成重载,但是会存在调用歧义,不调用不会报错

  • 如果类中没有显式定义构造函数,则C++编译器会自动生成一个无参的默认构造函数一旦用户显式定义编译器将不再生成(对内置类型而言初始化为未定义值,因为C++标准没有规定,取决于各编译器实现)

1.2 默认构造函数

  1. 无参构造函数

  2. 全缺省构造函数

  3. 我们没写编译器自动生成的构造函数

总结:不传参数就可以调用的函数叫做默认构造函数

三个只能存在一个

没有默认构造,就会报错

实践当中该初始化还是得初始化

C++11的补丁

【总结】

  1. 一般情况下构造函数都需要我们显式地去实现

  2. 只有少数情况下可以让编译器自动生成构造函数

例:MyQueue,成员大多是自定义类型Stack,内置类型可以给缺省值

2 析构函数

2.1 特性补充

无参数无返回值类型

一个类只能有一个析构函数,析构函数不能重载

【Q】所有类都需要写析构函数吗?

【A】不是,比如日期类,没有资源需要清理

2.2 编译器自动生成的析构函数

特性和构造函数类似:内置类型不做处理,自定义类型去调用对应析构

【实践总结】

  • 有资源需要显式清理,就需要写析构,如:Stack, List...

  • 有两种场景不需要写析构,默认生成就可以

    • 没有资源需要清理,如:Date

    • 内置类型成员没有资源需要清理,剩下都是自定义类型成员,如:MyQueue

3 拷贝构造

3.1 示例

3.2 自定义类型传值、指针、引用传参

语法逻辑上下面会造成无穷递归(实际上编译器会强制检查),所以拷贝的参数必须用引用

3.3 const关键字的引入

3.3.1 场景引入

构造函数内赋值左右顺序不慎写反:

运行结果:

3.3.2 加入const

定义拷贝构造函数时,如果参数前加上 const,这意味着承诺不会修改传入的对象

3.4 等价形式

3.5 浅拷贝

未显式定义Date类的拷贝构造函数,编译器自动生成的默认构造函数也可以完成,且不会报错

但对于Stack类而言,需要显式地写拷贝构造,否则默认生成的只会进行浅拷贝,即复制对象时只复制指向数据的指针,而不复制指针所指向的实际数据。这意味着原始对象和拷贝对象共享同一份数据

3.5.1 浅拷贝带来的问题

  1. 数据共享:

    1. 如果栈中的元素是指针,则浅拷贝会导致两个栈共享同一份数据。当其中一个栈删除元素时,另一个栈中的相应元素也会受到影响,因为它们指向相同的内存位置。

  2. 资源泄露:

    1. 如果栈中的元素是指针,并且这些指针指向动态分配的内存,那么浅拷贝会导致这些内存被多个对象共享。当其中一个对象销毁时,如果释放了内存,而其他对象仍然持有指向该内存的指针,则会导致悬挂指针或资源泄露。

  3. 双删问题:

    1. 如果栈中的元素指向动态分配的内存,那么浅拷贝会导致多个对象持有指向同一块内存的指针。当其中一个对象删除该内存时,其他对象再尝试删除这块内存就会导致双删问题,这通常会导致程序崩溃。

  4. 破坏封装性:

    1. 浅拷贝可能会破坏封装性,因为对象之间的状态变得相互依赖。这使得对象更难维护和测试。

  5. 异常安全问题:

    1. 如果在深拷贝过程中发生异常(例如内存不足),浅拷贝可能会留下不完整或无效的对象状态。

3.5.2 解决办法(深拷贝)

为了防止这些问题,通常需要实现深拷贝。对于栈中的每个元素,如果元素是指针,那么需要复制指针所指向的数据,而不是仅仅复制指针本身。例如,如果栈中存储的是指向字符串的指针,那么应该创建新的字符串副本,并更新指针指向新副本

【总结】

  1. 如果没有管理资源,一般情况不需要写拷贝构造,默认生成的拷贝构造就可以。如:Date

  2. 如果都是自定义类型成员,内置类型成员没有指向资源,默认生成的拷贝构造就可以。如:MyQueue

  3. 一般情况下,不需要显式写析构函数,就不需要写拷贝构造

  4. 如果内部有指针或者一些值指向资源,需要显式写析构释放,通常就需要显式写构造完成深拷贝。如:Stack Queue list等

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值