构造函数
构造函数是在创建类的新对象时自动调用的函数,用于初始化对象的状态。构造函数的名称与类名相同,没有返回类型。
基本构造函数类型:
- 默认构造函数:
- 定义:没有参数的构造函数,或者是所有参数都有默认值的构造函数。
- 用途:用于创建未指定初始状态的对象,或者当容器类如
std::vector
添加元素时,如果没有提供自定义构造函数,则调用默认构造函数初始化新元素。
class MyClass { public: MyClass() { /* 初始化工作 */ } // 默认构造函数 };
- 带参数构造函数:
- 定义:带有参数的构造函数,用于根据传递的参数初始化对象。
- 用途:创建对象时直接初始化成员变量至特定值。
class MyClass { private: int value; public: MyClass(int v) : value(v) { /* 使用v初始化value */ } // 带参数构造函数 };
拷贝构造函数
拷贝构造函数是一种特殊的构造函数,它用于创建一个新对象,新对象是现有对象的副本。拷贝构造函数只有一个参数,该参数是对同类类型对象的引用(通常为const引用)。
默认拷贝构造函数:
- 定义:编译器自动提供的拷贝构造函数,如果程序员没有显式定义拷贝构造函数的话。
- 行为:逐个成员进行浅拷贝(对于内置类型直接复制值,对于指针类型复制指针本身,不复制指针所指向的数据)。
- 示例:
class MyClass { private: int* data; public: // 编译器自动生成的默认拷贝构造函数 // MyClass(const MyClass& other) { data = other.data; } // 浅拷贝,不安全,不推荐使用未显式定义的拷贝构造函数 };
自定义拷贝构造函数:
- 定义:程序员显式定义的拷贝构造函数,以实现深拷贝或其他定制化复制逻辑。
- 示例:
class MyClass { private: int* data; // 假设data指向动态分配的内存 public: MyClass(const MyClass& other) { data = new int(*other.data); // 深拷贝,复制指针指向的数据 } // 必须记得定义相应的析构函数以释放动态内存 ~MyClass() { delete data; } };
区别与异同:
- 共同点:两者都是构造函数,都在创建新对象时调用。
- 不同点:
- 目的不同:默认构造函数主要用于初始化新对象至默认状态,而拷贝构造函数用于根据现有对象完全复制一个新的对象。
- 参数不同:默认构造函数无参数或参数全部有默认值,拷贝构造函数有一个同类对象的引用作为参数。
- 资源管理要求不同:拷贝构造函数需要特别关注资源管理问题,尤其是当类内部包含指针或其他资源持有者时,需确保深拷贝或正确转移资源所有权,避免出现悬挂指针或资源泄漏。而默认构造函数通常不需要关心这类问题。
构造函数的主要任务是初始化对象,而拷贝构造函数是专门负责复制已有对象的构造函数,其中默认拷贝构造函数由编译器自动提供,但往往需要根据实际情况自定义以确保复制行为正确有效。