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

C++的6种构造函数

在 C++ 中,构造函数是一种特殊的成员函数,用于初始化类对象。在对象创建时自动调用,构造函数的主要作用是分配资源、初始化数据成员等。根据不同的功能和使用场景,C++ 提供了多种类型的构造函数:

1. 默认构造函数 (Default Constructor)

默认构造函数不接受任何参数,或者所有参数都有默认值。当你创建对象时如果不指定参数,就会调用默认构造函数。

特点

  • 如果类没有定义任何构造函数,编译器会自动生成一个默认构造函数。
  • 如果类有其他构造函数但没有显式定义默认构造函数,编译器不会生成默认构造函数。

示例

class MyClass {
public:MyClass() { // 默认构造函数x = 0;}
private:int x;
};MyClass obj; // 自动调用默认构造函数

2. 参数化构造函数 (Parameterized Constructor)

参数化构造函数允许在创建对象时传递参数,用于初始化对象的成员变量。

特点

  • 通过传递参数,可以灵活地为对象赋值。

示例

class MyClass {
public:MyClass(int val) { // 参数化构造函数x = val;}
private:int x;
};MyClass obj(10); // 使用参数化构造函数

3. 拷贝构造函数 (Copy Constructor)

拷贝构造函数用于创建对象时,用一个已存在的对象来初始化新对象。其形式为接受一个对象的常量引用。

特点

  • 如果没有显式定义,编译器会自动生成一个默认的拷贝构造函数。
  • 主要用于复制对象的值,特别是对于动态分配内存的类,手动定义拷贝构造函数可以防止浅拷贝问题。

示例

class MyClass {
public:MyClass(int val) : x(val) {} // 参数化构造函数MyClass(const MyClass &obj) { // 拷贝构造函数x = obj.x;}
private:int x;
};MyClass obj1(10);
MyClass obj2 = obj1; // 使用拷贝构造函数

4. 移动构造函数 (Move Constructor)

移动构造函数是在 C++11 引入的,用于通过"移动语义"来避免拷贝操作,从而提高程序的性能,特别是涉及动态分配资源的对象。

特点

  • 接受一个右值引用 (T&&)。
  • 用于将资源从一个临时对象“移动”到新的对象中,通常通过偷取资源而不是复制它们。

示例

class MyClass {
public:MyClass(int val) : x(new int(val)) {} // 动态分配内存MyClass(MyClass&& obj) noexcept { // 移动构造函数x = obj.x;obj.x = nullptr; // 释放临时对象的所有权}~MyClass() { delete x; }
private:int* x;
};MyClass obj1(10);
MyClass obj2 = std::move(obj1); // 使用移动构造函数

5. 委托构造函数 (Delegating Constructor)

委托构造函数是在一个构造函数中调用同一个类的另一个构造函数,从而避免代码重复。这是 C++11 引入的特性。

特点

  • 可以简化多个构造函数之间的代码逻辑,避免重复代码。

示例

class MyClass {
public:MyClass() : MyClass(0) { // 委托给参数化构造函数// 可以额外执行一些操作}MyClass(int val) : x(val) {} // 参数化构造函数
private:int x;
};MyClass obj; // 调用默认构造函数,委托给参数化构造函数

6. 显式构造函数 (Explicit Constructor)

explicit 构造函数用于防止隐式类型转换。这对防止错误的自动类型转换特别有用。

特点

  • 防止构造函数被自动调用进行隐式转换。

示例

class MyClass {
public:explicit MyClass(int val) : x(val) {} // 显式构造函数
private:int x;
};MyClass obj1(10); // OK
MyClass obj2 = 10; // 错误,显式构造函数禁止隐式转换

7. 析构函数 (Destructor)

虽然析构函数不算构造函数,但与其作用类似。析构函数用于在对象生命周期结束时释放资源。析构函数没有参数,且前面有 ~ 符号。

示例

class MyClass {
public:MyClass() { x = new int(10); }~MyClass() { delete x; } // 析构函数
private:int* x;
};

总结:

C++ 中构造函数的类型和用途可以总结如下:

  • 默认构造函数: 初始化对象,通常不需要参数。
  • 参数化构造函数: 通过传参初始化对象的成员。
  • 拷贝构造函数: 通过已有对象初始化新对象。
  • 移动构造函数: 移动对象的资源,避免不必要的拷贝。
  • 委托构造函数: 在一个构造函数中调用另一个构造函数。
  • 显式构造函数: 防止隐式类型转换。

这些构造函数为对象的初始化提供了灵活的选择,尤其在管理资源时,合理使用拷贝和移动构造函数可以显著提升程序的效率。

相关文章:

  • 分享国产32位单片机的电机控制方案
  • Ovis1.6-9B视觉大模型环境搭建推理
  • 实验报告2-前端框架和模板引擎实现视图
  • Kali Linux入门教程(非常详细)从零基础入门到精通,看完这一篇就够了。
  • 【并发】ThreadLocal 为什么会内存泄露
  • WAF,全称Web Application Firewall,好用WAF推荐
  • Ubuntu上安装Git:简单步骤指南
  • 字母象形:十分有趣的单词扩展逻辑
  • 联想电脑怎么开启vt_联想电脑开启vt虚拟化教程(附intel和amd主板开启方法)
  • 等保测评:企业数字安全的坚实盾牌
  • 【2024.9.29练习】R 格式
  • 在Spring项目中使用MD5对数据库加密
  • 【计算机网络】详解HTTP请求和响应格式常见请求方法Header报头响应报文状态码URL
  • C语言-进程控制编程
  • ceph rgw 桶分片之reshard
  • [原]深入对比数据科学工具箱:Python和R 非结构化数据的结构化
  • 2017 前端面试准备 - 收藏集 - 掘金
  • Apache的80端口被占用以及访问时报错403
  • const let
  • Fabric架构演变之路
  • java架构面试锦集:开源框架+并发+数据结构+大企必备面试题
  • LeetCode算法系列_0891_子序列宽度之和
  • miniui datagrid 的客户端分页解决方案 - CS结合
  • Netty 框架总结「ChannelHandler 及 EventLoop」
  • Redis中的lru算法实现
  • vue-router 实现分析
  • 表单中readonly的input等标签,禁止光标进入(focus)的几种方式
  • 缓存与缓冲
  • 理解在java “”i=i++;”所发生的事情
  • 码农张的Bug人生 - 见面之礼
  • 前端每日实战:61# 视频演示如何用纯 CSS 创作一只咖啡壶
  • 使用阿里云发布分布式网站,开发时候应该注意什么?
  • 详解移动APP与web APP的区别
  • ​2020 年大前端技术趋势解读
  • ​云纳万物 · 数皆有言|2021 七牛云战略发布会启幕,邀您赴约
  • # MySQL server 层和存储引擎层是怎么交互数据的?
  • (35)远程识别(又称无人机识别)(二)
  • (52)只出现一次的数字III
  • (delphi11最新学习资料) Object Pascal 学习笔记---第7章第3节(封装和窗体)
  • (读书笔记)Javascript高级程序设计---ECMAScript基础
  • (十六)一篇文章学会Java的常用API
  • (十一)图像的罗伯特梯度锐化
  • (四)c52学习之旅-流水LED灯
  • (四)docker:为mysql和java jar运行环境创建同一网络,容器互联
  • (转载)虚函数剖析
  • ***通过什么方式***网吧
  • ./configure、make、make install 命令
  • ./include/caffe/util/cudnn.hpp: In function ‘const char* cudnnGetErrorString(cudnnStatus_t)’: ./incl
  • .NET Core中Emit的使用
  • .net 发送邮件
  • .net 反编译_.net反编译的相关问题
  • .net 连接达梦数据库开发环境部署
  • .NetCore项目nginx发布
  • .NET开发人员必知的八个网站
  • [001-03-007].第07节:Redis中的事务