【C++】构造函数和初始化列表的性能差距
构造函数和初始化列表的性能差距对比测试
1.说明
在C++类和对象中,你可能听到过更加推荐用初始化列表来初始化类内成员。如果类内成员是自定义类型,则只能在初始化列表中调用自定义类型的构造函数。
但初始化列表和在构造函数体内直接赋值有无性能差距呢?今天就用一份相对简单的代码来测试一下
2.测试
2.1 代码说明
首先是一个自定义类型,实现带缺省值的默认构造,拷贝构造和赋值重载这三个函数,并在内部新增打印来区分不同的函数
struct mytest {
public:mytest(int a = -1){_a = a;cout << "mytest() " << a << endl;}mytest(const mytest& st) {_a = st._a;cout << "mytest(copy) " << st._a << endl;}mytest& operator=(const mytest& st){_a = st._a;cout << "mytest operator= " << st._a << endl;return *this;}
private:int _a;
};
再在另外一个类中使用这个自定义类型
struct myclass {
public:myclass(const struct mytest& st, int b){cout << "myclass() _b:" << _b << endl;}struct mytest _sa;int _b;
};
此时构造函数就有两种写法,一种是在初始化列表中初始化这个自定义类型
myclass(const struct mytest& st, int b):_sa(st),_b(b){cout << "myclass() _b:" << _b << endl;}
另外一种是在构造函数体内通过赋值重载来初始化这个自定义类型
myclass(const struct mytest& st, int b){_sa = st;_b = b;cout << "myclass() _b:" << _b << endl;}
需要注意的是,这里的自定义类型传参采用了引用传参,并不会因此产生额外的拷贝!
主函数体如下,为了区分第一个mytest的构造函数,我在其后新增了一行输出作为分割
int main()
{mytest test_a(1);cout << "------" << endl;myclass test(test_a, 3);return 0;
}
2.2 测试
先来看看使用赋值初始化的方式,可以看到,虽然我们在初始化列表中什么都没有写,但是这里依旧调用了默认的构造函数(因为默认构造函数的缺省值给的是-1,这里能通过参数判断出来这并不是我们显式调用的构造)
调用了默认构造后,又通过赋值重载来初始化了一遍_sa,相当于两次初始化

但如果调用初始化列表,则只会有一次拷贝构造,避免了额外的默认构造调用!

在linux下也测试过了,结果和VS2019相同
3.结论
结论就出来了:初始化列表能节省一次默认构造的调用,优化性能!
3.1 实际场景
在上面的场景中,性能差距可能并不会特别大,但是在下面的场景中可能就不一样了
struct mytest {
public:mytest(int sz = 1){_str = new char[sz];_sz = sz;cout << "mytest() " << sz << endl;}mytest(const mytest& st) {delete _str;// 需要先销毁原视的数据_str = new char[st._sz]; // 再创建一个新的_sz = st._sz;//省略拷贝数据的代码cout << "mytest(copy) " << st._sz << endl;}mytest& operator=(const mytest& st){delete _str;// 需要先销毁原视的数据_str = new char[st._sz]; // 再创建一个新的//省略拷贝数据的代码cout << "mytest& operator= " << st._sz << endl;return *this;}
private:char* _str;size_t _sz;
};struct myclass {
public:myclass(const struct mytest& st, int b):_sa(st),_b(b){//_sa = st;//_b = b;cout << "myclass() _b:" << _b << endl;}struct mytest _sa;int _b;
};
在这个场景中,因为mytest自定义类型的拷贝构造涉及到了深拷贝,此时就需要将已有的空间给销毁了,再new一片新的空间出来,再将数据给拷贝过去。
白白多了一层默认构造中的new空间的+拷贝构造中delete原有空间的消耗!
如果类中需要深拷贝的成员不止一个,那性能差距就更大!
所以在C++中,一律以初始化列表优先!
这里顺带提一嘴初始化列表的小坑,也算是复习;
当你使用初始化列表来初始化类内成员的时候,初始化的顺序是类内成员声明的顺序,而不是初始化列表中的顺序!这点非常重要,如果顺序不对,可能会出现使用未定义(还没有初始化完成)的参数的bug!
相关文章:
【C++】构造函数和初始化列表的性能差距
构造函数和初始化列表的性能差距对比测试 1.说明 在C类和对象中,你可能听到过更加推荐用初始化列表来初始化类内成员。如果类内成员是自定义类型,则只能在初始化列表中调用自定义类型的构造函数。 但初始化列表和在构造函数体内直接赋值有无性能差距呢…...
Linux下套接字TCP实现网络通信
Linux下套接字TCP实现网络通信 文章目录 Linux下套接字TCP实现网络通信1.引言2.具体实现2.1接口介绍1.socket()2.bind()3.listen()4.accept()5.connect() 2.2 服务器端server.hpp2.3服务端server.cc2.4客户端client.cc 1.引言 套接字(Socket)是计算机网络中实现网络通信的一…...
❤ vue清除定时器Bug
❤ vue清除定时器Bug 页面加载,清除定时器 clearTimeout(intm) 问题 遇见的需求是:webapp 从A页面进入B页面,B页面点击按钮,加载完B页面的加载效果进入c,从C页面返回A页面,仍然显示B页面的加载效果 结果定时器一直…...
IDEA创建Spring,Maven项目没有resources文件夹
有时新建Spring或Maven项目时,会出现目录中main下无resources文件夹的情况,来一起解决一下: FIles|Project Structure 在Modules模块找到对应路径,在main下创建resources,右键main,选择新文件夹 输入文件…...
Unity 结构少继承多组合
为什么不推荐使用继承? 继承是面向对象的四大特性之一,用来表示类之间的 is-a 关系,可以解决代码复用的问题。虽然继承有诸多作用,但继承层次过深、过复杂,也会影响到代码的可维护性。所以,对于是否应该在…...
保研之旅2:中科院声学所“声学和信息学科”夏令营
💥💥💞💞欢迎来到本博客❤️❤️💥💥 本人持续分享更多关于电子通信专业内容以及嵌入式和单片机的知识,如果大家喜欢,别忘点个赞加个关注哦,让我们一起共同进步~ &#x…...
android adb自动连接手机安装apk bat
1.新建bat文件adb echo off:apk文件名称 在setting.txt获取 set apkFileName"":设置文件 set settingFileE:\apk\bat\setting.txt:启动页面 applicationid/启动页面路径 set startActivitycom.aaa.aaa/com.aaa.aaa.ui.common.SplashActivity:读取settingFile第一行的…...
用心维护好电脑,提高学习工作效率
无论是学习还是工作,电脑都是IT人必不可少的重要武器,一台好电脑除了自身配置要经得起考验,后期主人对它的维护也是决定它寿命的重要因素! 一、我的电脑 系统制造商: ASUSTeK COMPUTER INC. 系统型号: ZenBook UX481FAY 1.1 如…...
以太坊硬分叉后的可重入漏洞攻击
以太坊硬分叉后的可重入漏洞攻击 以太坊君士坦丁堡升级将降低部分 SSTORE 指令的 gas 费用。然而,这次升级也有一个副作用,在 Solidity 语言编写的智能合约中调用 address.transfer()函数或 address.send()函数时存在可重入漏洞。在目前版本的以太坊网络…...
k8s 常用命令(三)
1、查看版本信息:kubectl version [rootmaster ~]# kubectl version [rootmaster ~]# kubectl version Client Version: version.Info{Major:"1", Minor:"21", GitVersion:"v1.21.3", GitCommit:"ca643a4d1f7bfe34773c74f7952…...
API 网关基础
目录 一、网关概述二、网关提供的功能三、常见网关系统3.1 Netflix Zuul3.2 Spring Cloud Gateway3.3 Kong3.4 APISIX3.5 Shenyu 一、网关概述 API网关是一个服务器,是系统的唯一入口。 从面向对象设计的角度看,它与外观模式类似。API网关封装了系统内部…...
【Linux】权限问题
Linux权限 一、Linux 权限的概念二、Linux 权限管理1. 文件访问者的分类2. 文件类型和访问权限(事物属性)3. 文件访问权限的相关设置方法 三、默认权限1. 对文件和目录进行操作需要的权限2. 文件和目录的默认权限3. 粘滞位 一、Linux 权限的概念 Linux …...
线性代数的学习和整理10:各种特殊类型的矩阵(草稿-----未完成 建设ing)
目录 1 图形化分类 1.1对称矩阵 1.2 梯形矩阵 1.3 三角矩阵 1.3.1 上三角矩阵 1.4 对角线矩阵 2 按各自功能分 2.1 等价矩阵 2.2 增广矩阵 2.3 伴随矩阵 2.4 正交矩阵 2.5 正交矩阵 2.6 相似矩阵 1 图形化分类 1.1对称矩阵 1.2 梯形矩阵 1.3 三角矩阵 1.3.1 上…...
Go 自学:变量、函数、结构体、接口、错误处理
1. 打印变量数据类型 package mainimport "fmt"func main() {penniesPerText : 2.0fmt.Printf("The type of penniesPerText is %T\n", penniesPerText) }输出为: The type of penniesPerText is float64 2. 同时给多个变量赋值 package mai…...
pyqt Pyton VTK 使用 滑块 改变 VTK Actor 颜色
使用 PyQt5 vtk vtk球体 使用滑块 RGB 改变 Actor 颜色 CODE import sys from PyQt5.QtWidgets import * from PyQt5.QtWidgets import (QApplication, QCheckBox, QGridLayout, QGroupBox,QMenu, QPushButton, QRadioButton, QVBoxLayout, QWidget, QSlider,QLineEdit,QLabe…...
春秋云镜 CVE-2019-16113
春秋云镜 CVE-2019-16113 Bludit目录穿越漏洞 靶标介绍 在Bludit<3.9.2的版本中,攻击者可以通过定制uuid值将文件上传到指定的路径,然后通过bl-kernel/ajax/upload-images.php远程执行任意代码。 启动场景 漏洞利用 exp https://github.com/Kenun…...
【JavaEE基础学习打卡06】JDBC之进阶学习PreparedStatement
目录 前言一、PreparedStatement是什么二、重点理解预编译三、PreparedStatement基本使用四、Statement和PreparedStatement比较1.PreparedStatement效率高2.PreparedStatement无需拼接参数3.PreparedStatement防止SQL注入 总结 前言 📜 本系列教程适用于JavaWeb初学…...
Postgresql12基于时间点恢复
1、环境 centos 7系统 postgresql 12 docker 20.10.6 2、整体思路 1)进行一个pgdata目录的全量备份 2)通过wal日志恢复到故障发生之前某个时间点 3、操作步骤 配置postgresql.conf文件 #日志级别 wal_level replica #归档开关 archive_mode on …...
【MySQL系列】Select语句单表查询详解(二)ORDERBY排序
💐 🌸 🌷 🍀 🌹 🌻 🌺 🍁 🍃 🍂 🌿 🍄🍝 🍛 🍤 📃个人主页 :阿然成长日记 …...
C++学习第十九天----简单文件输入/输出和今日工作问题
1.写入到文本文件中 cout用于控制台输出; 必须包含头文件iostream; 头文件iostream定义了一个用于处理输出的ostream类; 头文件iostream声明了一个名为cout的ostream变量(对象); 必须指明名称空间std&…...
从‘量子电子商务’到三方协议:手把手拆解量子数字签名(QDS)的核心流程与实验挑战
量子数字签名:从理论到实验的技术深潜与挑战解析 量子数字签名(QDS)作为后量子密码学的重要分支,正在从实验室走向实际应用。不同于传统数字签名依赖数学难题的复杂性,QDS基于量子力学的基本原理,为信息安全…...
网易云音乐评论爬虫实战:破解加密接口抓取数据
一、接口分析:找准评论数据请求入口 在抓取网易云音乐歌曲评论时,我们不难发现,页面并不会随着翻页刷新跳转,评论的加载属于异步AJAX请求。这类接口有一个明显特点:接口地址固定不变,分页切换完全依靠请求载…...
SLAM Toolbox:从零开始掌握机器人自主定位与建图技术
SLAM Toolbox:从零开始掌握机器人自主定位与建图技术 【免费下载链接】slam_toolbox Slam Toolbox for lifelong mapping and localization in potentially massive maps with ROS 项目地址: https://gitcode.com/gh_mirrors/sl/slam_toolbox 在机器人技术飞…...
3步破解音乐平台碎片化困局:Listen1多源聚合技术深度实践
3步破解音乐平台碎片化困局:Listen1多源聚合技术深度实践 【免费下载链接】listen1_chrome_extension one for all free music in china (chrome extension, also works for firefox) 项目地址: https://gitcode.com/gh_mirrors/li/listen1_chrome_extension …...
Windows用户福音:WSL2+Docker快速部署Coze Studio开源版(附常见错误解决方案)
Windows平台高效部署Coze Studio开源版的完整指南 对于Windows开发者而言,在本地环境搭建Coze Studio开源版可能面临诸多挑战。本文将提供一套经过验证的完整解决方案,从WSL2配置到Docker优化,帮助您避开常见陷阱,快速实现Coze St…...
TMS320F280049系列文章之第二章 工程搭建实战:从零配置到路径设置的避坑指南
1. 工程准备与环境搭建 第一次接触TMS320F280049开发的朋友,可能会被复杂的工程配置劝退。别担心,跟着我的步骤走,保证你能顺利搭建第一个工程。我用的环境是CCS10.3.1和C2000Ware_4_01,这也是目前比较稳定的组合。 先说说准备工作…...
深度解析LSPosed框架:从Hook原理到模块开发的完整实战指南
深度解析LSPosed框架:从Hook原理到模块开发的完整实战指南 【免费下载链接】LSPosed_mod My changes to LSPosed 项目地址: https://gitcode.com/GitHub_Trending/ls/LSPosed_mod LSPosed框架作为Android系统Hook技术的现代实现,为开发者提供了强…...
从绝望到希望:3步拯救你的重要数据
从绝望到希望:3步拯救你的重要数据 【免费下载链接】testdisk TestDisk & PhotoRec 项目地址: https://gitcode.com/gh_mirrors/te/testdisk 当硬盘突然罢工,分区神秘消失,或者重要文件被误删时,那种感觉就像精心搭建的…...
从模型到服务:EasyAnimateV5 API开发完整解决方案
从模型到服务:EasyAnimateV5 API开发完整解决方案 1. 为什么需要API服务化 将AI模型封装为API服务是现代AI应用开发的关键步骤。对于EasyAnimateV5这样的图生视频模型,API化能带来多重价值: 降低使用门槛:非技术用户通过简单接…...
5分钟部署Llama Factory:开箱即用的大模型训练平台
5分钟部署Llama Factory:开箱即用的大模型训练平台 1. 为什么选择Llama Factory 在人工智能领域,大型语言模型(LLM)的微调和训练一直是技术门槛较高的工作。传统方法需要编写大量代码、处理复杂的环境配置,并且对硬件资源要求极高。Llama F…...
