当前位置: 首页 > news >正文

C++中,构造函数和析构函数

在C++中,构造函数和析构函数是类的重要组成部分,用于管理对象的生命周期和资源。以下是关键点的系统总结:

构造函数

  1. 作用
    初始化对象,在创建对象时自动调用,负责设置初始状态和分配资源。

  2. 命名与形式

    • 与类同名,无返回类型。
    • 可重载(多个不同参数的版本)。
    • 示例:
      class Car {
      public:
          Car();              // 默认构造函数
          Car(int speed);     // 参数化构造函数
      };
      
  3. 类型

    • 默认构造函数:无参数。若未定义任何构造函数,编译器会自动生成一个。
    • 拷贝构造函数:用同类对象初始化新对象,形式为 Car(const Car& other)
    • 移动构造函数(C++11):通过右值引用转移资源,形式为 Car(Car&& other)
    • 委托构造函数:调用同类其他构造函数,减少重复代码:
      MyClass() : MyClass(0) {}  // 委托给带参数的构造函数
      
  4. 初始化列表

    • 在构造函数体执行前初始化成员变量。
    • 必须用于 const 成员或引用成员:
      Example(int a, int b) : x(a), y(b) {}
      

析构函数

  1. 作用
    清理资源(如释放动态内存、关闭文件),在对象销毁时自动调用。

  2. 命名与形式

    • 类名前加 ~,无参数和返回值。
    • 每个类只能有一个析构函数。
    • 示例:
      ~Car() { /* 清理操作 */ }
      
  3. 关键场景

    • 动态内存管理:若类中有 new 分配的资源,需在析构函数中 delete
      ~String() { delete[] data; }
      
    • 继承中的虚析构函数:基类析构函数应声明为 virtual,确保正确调用派生类析构函数:
      class Base {
      public:
          virtual ~Base() {}  // 虚析构函数
      };
      

调用时机

  • 构造函数:对象创建时(局部变量、new、临时对象等)。
  • 析构函数:对象销毁时(作用域结束、delete、异常退出等)。

示例代码

#include <cstring>

class String {
private:
    char* data;
public:
    // 参数化构造函数
    String(const char* str) {
        data = new char[strlen(str) + 1];
        strcpy(data, str);
    }

    // 拷贝构造函数(深拷贝)
    String(const String& other) {
        data = new char[strlen(other.data) + 1];
        strcpy(data, other.data);
    }

    // 析构函数
    ~String() {
        delete[] data;
    }
};

int main() {
    String s1("Hello");     // 调用参数化构造函数
    String s2 = s1;         // 调用拷贝构造函数
    return 0;               // s1和s2析构,自动释放内存
}

注意事项

  1. 默认生成的函数
    若未定义,编译器会自动生成默认构造函数、拷贝构造函数、析构函数等。但默认拷贝构造函数是浅拷贝,可能引发问题(如双重释放内存)。

  2. 深拷贝与浅拷贝
    若类管理资源(如指针),需自定义拷贝构造函数和赋值运算符,实现深拷贝。

  3. 虚析构函数
    基类必须声明虚析构函数,确保通过基类指针删除派生类对象时,正确调用派生类析构函数。


通过合理使用构造函数和析构函数,可以确保对象的正确初始化和资源的安全释放,避免内存泄漏和未定义行为。

相关文章:

  • 初识HTTP
  • 一维前缀和与二维前缀和的详细用法和介绍
  • 局域网设备访问虚拟机 挂载NFS
  • 算法刷题记录——LeetCode篇(7) [第601~700题](持续更新)
  • dify创建第一个Agent
  • cmakelist中添加opencv
  • 【css酷炫效果】纯CSS实现科技感网格背景
  • 基于ros2与moveit2开发的yolo识别抓取虚拟机械臂
  • 开源模型:加速构建智能生态,引领人工智能新未来
  • Linux系统管理与编程07:任务驱动综合应用
  • 【鸿蒙开发】Hi3861学习笔记- UDP客户端
  • 第十六届蓝桥杯康复训练--6
  • C语言入门教程100讲(7)类型转换
  • 【算法学习计划】动态规划 -- 背包问题(01背包和完全背包)
  • git工作区、暂存区、本地仓库、远程仓库的区别和联系
  • 在Android Studio中,如何快速为变量添加m?
  • Vue3 0基础入门,三分钟掌握vue3核心知识
  • CentOS8 安装 Docker-CE
  • How to install samba on Linux mint 22.1
  • 字节跳动算法高频题:动态规划最优模板
  • 深圳中院回应“退休夫妻月入1.2万负债1.2亿”:其自述因经营不善负债
  • 孙简任吉林省副省长
  • 飙升至熔断,巴基斯坦股市两大股指收盘涨逾9%
  • 香港将展“天方奇毯”,从地毯珍品看伊斯兰艺术
  • 被流量绑架人生,《人生开门红》能戳破网络时代的幻象吗
  • 墨西哥宣布就“墨西哥湾”更名一事起诉谷歌