构造函数与析构函数

article/2025/10/2 6:16:54

一,引言

由于c语言常常会忘记初始化与销毁,造成许多麻烦。所以c++就引入了构造函数与析构函数,分别用来完成初始化与清理工作,且由编译器自动调用,这就避免了许多麻烦。

二,构造函数

构造函数是一个特殊的成员函数,名字与类名相同,创建类类型对象时由编译器自动调用,主要完成初始化工作保证每个数据成员都有 一个合适的初始值,并且在对象整个生命周期内只调用一次

构造函数特点如下:

1,函数名与类名相同。

2,无返回值。

3,对象实例化时编译器自动调用对应的构造函数。

4,构造函数可以重载

class Date
{
public:// 1.无参构造函数Date(){}// 2.带参构造函数Date(int year, int month, int day){_year = year;_month = month;_day = day;}
private:int _year;int _month;int _day;
};int main()
{Date d1; // 调用无参构造函数Date d2(2015, 1, 1); // 调用带参的构造函数Date d3();    #不能这么写,会报错!!!
}

注意:如果通过无参构造函数创建对象时,对象后面不用跟括号,否则就成了函数声明,该函数无参,返回一个日期类型的的对象

5,无参的构造函数和全缺省的构造函数都称为默认构造函数,且防止冲突默认构造函数只能有一个

class Date
{
public:#无参Date(){_year = 1900;_month = 1;_day = 1;}#全缺省Date(int year = 1900, int month = 1, int day = 1){_year = year;_month = month;_day = day;}private:int _year;int _month;int _day;
};
注意:无参构造函数、全缺省构造函数、我们没写编译器默认生成的构造函数,都可以认为
是默认构造函数

6,如果类中没有显式定义构造函数,则C++编译器会自动生成一个无参的默认构造函数,一旦用户显式定义编译器将不再生成

class Date
{
public:/*// 如果用户显式定义了构造函数,编译器将不再生成Date(int year, int month, int day){_year = year;_month = month;_day = day;}*/private:int _year;int _month;int _day;
};int main()
{Date d1;return 0;
}

将Date类中构造函数屏蔽后,代码可以通过编译,因为编译器生成了一个无参的默认构造函数。将Date类中构造函数放开,代码编译失败,因为一旦显式定义任何构造函数,编译器将不再生成无参构造函数,Date类中的构造函数不是无参构造函数和全缺省构造函数,即不属于默认构造函数。若d1不进行传参,放开后报错,因为没有合适的默认构造函数可用。

对默认构造函数正确的态度应该是:面向需求编译器默认生成就可以满足,就不用自己写,不满足就需要自己写 


7,C++把类型分成内置类型和自定义类型。内置类型就是语言提供的数据类型,如:int /char...,自定义类型就是我们使用class /struct /union等自己定义的类型。

不实现构造函数的情况下,编译器默认生成的构造函数只对自定义类型进行初始化,而内置类型不进行处理,只会给予随机值。

这是当初设计时留下的bug,无法进行修改。只能针对内置类型成员不初始化的缺陷,打补丁,即:内置类型成员变量在类中声明时可以给默认值

class Date
{
private:// 内置类型int _year = 1;     //这里不是初始化,而是缺省值int _month = 1;int _day = 1;// 自定义类型Time _t;
};

给了缺省值后,内置类型就可以初始化了

关于编译器生成的默认构造函数

  • 例:time类显式定义默认构造函数,Date类不显式定义默认构造函数,date类中包含一个time类对象。
  • 自定义类型成员初始化过程:初始化time对象的时候不是编译器直接去调用time类中定义的构造函数,而是先给date类生成默认构造函数,然后在date类的默认构造函数中再去调用time类中我们自己显式定义的默认构造函数。这个过程自定义类型成员必须要有显式默认构造函数,否则编译器不会给date类生成默认构造函数
  • 所以编译器生成的默认构造函数就是:生成一个函数去调用自定义类型成员的显式默认构造函数

三,析构函数

析构函数:与构造函数功能相反,析构函数不是完成对对象本身的销毁,局部对象销毁工作是由
编译器完成的。而 对象在销毁时会自动调用析构函数,完成对象中资源的清理工作。
析构函数特性如下:
  1. 析构函数名是在类名前加上字符 ~
  2. 无参数无返回值类型。
  3. 一个类只能有一个析构函数。若未显式定义,系统会自动生成默认的析构函数。注意:析构函数不能重载
  4. 对象生命周期结束时,C++编译系统系统自动调用析构
  5. 多个对象调用析构函数的顺序和创建顺序相反,哪个对象先压栈哪个对象先销毁。
class Time
{
public:#析构函数~Time(){cout << "~Time()" << endl;}
private:int _hour;int _minute;int _second;
};class Date
{
private:// 内置类型int _year = 1970;int _month = 1;int _day = 1;// 自定义类型Time _t;
};int main()
{Date d;return 0;
}

 

默认析构函数清理规则

  • 同构默认生成构造函数类似 ,默认生成的析构函数同样对内置类型的成员变量不做处理,只在对象销毁时对自定义类型的成员会调用它们的析构函数来清理该自定义函数的成员变量。
如果类中没有申请资源时,析构函数可以不写,直接使用编译器生成的默认析构函数,比如
Date类;有资源申请时,一定要写,否则会造成资源泄漏。

http://chatgpt.dhexx.cn/article/mKqHlTTr.shtml

相关文章

构造函数和析构函数

文章目录 前言 1.构造函数<1>概念<2>特性 2.初始化列表<1>概念<2>特征 3.析构函数<1>概念<2.>特征 前言 如不清楚类的定义可以点击此篇文章&#xff1a;类的定义与引入 C为很么要引入构造函数和析构函数呢&#xff0c;前文讲到大佬引入了…

C++ 构造函数和析构函数 详解

目录 概述构造函数的分类1. 无参(默认)构造函数2. 有参构造函数3. 委托构造函数4. 复制(拷贝)构造函数5. 移动构造函数 构造函数调用规则析构函数 概述 C中用构造函数和析构函数来初始化和清理对象&#xff0c;这两个函数将会被编译器自动调用。对象的初始化和清理是非常重要的…

java异常处理及自定义异常

异常处理的实际上就是&#xff1a; 有风险的行为&#xff08;方法&#xff09;可能会将异常抛出&#xff08;throws&#xff09;。调用该方法的程序会尝试&#xff08;try&#xff09;去运行,运行的同时捕捉&#xff08;catch&#xff09;异常。 简而言之&#xff0c;就是对有…

java异常 — — 自定义异常

三、自定义异常 3.1、概述 为什么需要自定义异常类: Java中不同的异常类分别表示看某一种具体的异常情况&#xff0c;那么在开发中总是有些异常情况是SUN没有定义好的此时我们根据自己业务的异常情况来定义异常类。例如年龄负数问题&#xff0c;考试成绩负数问题等等。 在上…

JAVA自定义异常处理

自定义异常处理可以分为两种&#xff0c;一种是自定义编译处理&#xff0c;另一种是自定义运行处理 1.自定义编译处理需要创建一个异常类用于继承Exception类 重写构造器 在出现异常的地方用throw new 自定义对象抛出 作用&#xff1a;编译时异常时编译阶段就报错&#xff…

Java的自定义异常类

Java的异常处理机制可以让程序具有极好的容错性&#xff0c;让程序更加健壮。当程序运行出 现意外情形时&#xff0c;系统会自动生成一个 Exception对象来通知程序&#xff0c;从而实现将“业务功 能实现代码”和“错误处理代码”分离&#xff0c;提供更好的可读性。 Java把所…

Java自定义异常及统一处理,信息返回

开始操作 创建enums&#xff0c;exception包&#xff1a; enums包下&#xff1a; 创建BaseCodeEnum接口 创建Response类&#xff1a;为统一信息返回类 创建ResponseCode枚举类&#xff1a;在这里定义我们需要的异常 exception包下&#xff1a; 创建HandlerException类&#…

Java自定义异常类统一处理异常

当程序发生异常时&#xff0c;会返回一大堆不友好的内容&#xff0c;非常不美观&#xff01; 我们在写代码的时候&#xff0c;对异常处理一般是try catch或者抛出异常throws Exception。 try catch大家都知道&#xff0c;代码中大量的try catch会占用内存影响性能&#xff0c…

Java中的自定义异常

代码实现 自定义异常类型主要实现代码 public class Exception_demo extends Exception{//自定义异常&#xff0c;需要把自定义异常类继承于Exception异常类&#xff0c;自定义异常类属于异常类的子类public Exception_demo(){//构造方法也叫做构造器&#xff0c;构造方法的名…

【Java异常】自定义异常

Java中定义了大量的异常类&#xff0c;虽然这些异常类可以描述编程时出现的大部分异常情况&#xff0c;但是在程序开发中有时可能需要描述程序中特有的异常情况,例如在设计divide()方法时不允许被除数为负数。为了解决这样的问题,Java允许用户自定义异常&#xff0c;但自定义的…

JAVA项目中自定义异常

JAVA项目中自定义异常 1.数据返回处理类 Data public class R<T> implements Serializable {private static final long serialVersionUID -8497670085742879369L;ApiModelProperty(value "返回码", example "200")private Integer code200;Api…

Java自定义异常理解

前言&#xff1a;看了许多博客和书&#xff0c;都对自定异常一笔带过&#xff0c;总让人感觉莫名奇妙&#xff0c;一直在问自己一个问题&#xff0c;我们能很好的解决异常就很不错了&#xff0c;为什么还要自己自定义异常&#xff0c;让自己去自找麻烦呢&#xff1f;后来我才理…

Java自定义异常

使用Java内置的异常类可以描述在编程时出现的大部分异常情况。除此之外&#xff0c;用户还可以自定义异常。用户自定义异常类&#xff0c;只需继承Excepition类即可 在程序当中自定义异常类&#xff0c;大体可以分成几个步骤&#xff1a; 1.创建自定义异常类 2.在方法中通过t…

JAVA 基础学习之异常机制

异常机制 1、概念 异常指程序运行过程中出现的非正常现象&#xff0c;例如用户输入错误、除数为零、需要处理的文件不存在、数组下标越界等。在Java的异常处理机制中&#xff0c;引进了很多用来描述和处理异常的类&#xff0c;称为异常类。 2、异常的分类 Throwable下面又派生…

【Java】自定义异常

自定义异常&#xff1a; java提供的异常类&#xff0c;不够我们使用&#xff0c;需要自己定义一些异常类 格式&#xff1a; public class XXException extends Exception|RuntimeException{ 添加一个空参数的构造方法 添加一个带异常信息的构造方法 } 注意&#xff1a; 1.自…

Java异常详解及自定义异常

我已经不用 try catch 处理异常了&#xff01;太烦人了_51CTO博客_try catch处理什么异常 一、异常的概念 1.定义&#xff08;什么是异常&#xff1f;&#xff09; 异常是例外&#xff0c;是一个程序在执行期间发生的事件&#xff0c;它中断正在执行程序的正常指令流。软件开发…

哈夫曼树(带权路径长度+树的带权路径长度+哈夫曼树定义+构造哈夫曼树+哈夫曼树性质+哈夫曼编码+计算平均码长-这里指WPL)

带权路径长度 树的带权路径长度WPL 哈夫曼树 哈夫曼树构造 哈夫曼树性质 哈夫曼编码 固定长度编码 可变长编码 前缀编码 固定长度编码、可变长编码、前缀编码、哈夫曼编码 思维倒图 试题

哈夫曼树——【实例】利用3,6,8,12,5,7这六个值作为叶子结点的权,由该权值集合构造的哈夫曼树中带权路径长度之和为多少,该树的深度为多少。

利用3&#xff0c;6&#xff0c;8&#xff0c;12&#xff0c;5&#xff0c;7这六个值作为叶子结点的权&#xff0c;由该权值集合构造的哈夫曼树中带权路径长度之和为多少&#xff0c;该树的深度为多少。 基础知识 哈夫曼树是一种带权路径长度最短的二叉树&#xff0c;也称为最优…

哈夫曼树(最优二叉树:带权路径长度最短的树(度相同的情况下))

基本概念 1、结点的路径长度&#xff1a;两结点间间路径上的分支数 2、树的路径长度&#xff1a;从根结点到每一个结点的路径长度之和 3、结点的带权路径长度&#xff1a;从根结点到该结点之间的路径长度与该结点的权的乘积 4、树的带权路径长度&#xff1a;树中所有叶子结…

已知权值的哈夫曼树,求带权路径长度

转自牛客网 有权值分别为11&#xff0c;8&#xff0c;6&#xff0c;2&#xff0c;5的叶子结点生成一棵哈夫曼树&#xff0c;它的带权路径长度为_______。