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

类和对象(四)

构造函数中的初始化列表

之前在实现构造函数时,主要是在函数体内进行赋值,而构造函数还有另一种初始化方式,通过初始化列表进行初始化。

初始化列表的使⽤⽅式是以⼀个冒号开始,接着是⼀个以逗号分隔的数据成员列表,每个"成员变量"后⾯跟⼀个放在括号中的初始值或表达式。每个成员变量在初始化列表中只能出现⼀次,语法理解上初始化列表可以认为是每个成员变量定义初始化的地⽅。

要注意的是,初始化列表中按照成员变量在类中声明顺序进行初始化,跟成员在初始化列表出现的的先后顺序是无关的。但一般建议声明顺序和初始化列表顺序保持⼀致。

#include<iostream>class Date
{
public:Date(int year = 1, int month = 1, int day = 1):_year(year), _month(month), _day(day){}void Print(){std::cout << _year << "-" << _month << "-" << _day << std::endl;}private:int _year;int _month;int _day;
};int main()
{Date d1(2024, 7, 20);d1.Print();return 0;
}

要区分,函数参数中给的缺省值并不能初始化成员变量。两者是不同的东西,要加一区分。

#include<iostream>class Date
{
public:Date(int year = 1, int month = 1, int day = 1):_year(year), _month(month){}void Print(){std::cout << _year << "/" << _month << "/" << _day << std::endl;}private:int _year;int _month;int _day;
};int main()
{Date d1(2024, 7, 20);d1.Print();return 0;
}

这里 _day 并未初始化,为随机值。

#include<iostream>class Date
{
public:Date(int year = 1, int month = 1, int day = 1):_year(year), _month(month){// _day未在初始化列表中初始化,在函数体内也能初始化,如果都没有就为随机值_day = day;}void Print(){std::cout << _year << "/" << _month << "/" << _day << std::endl;}private:int _year;int _month;int _day;
};int main()
{Date d1(2024, 7, 20);d1.Print();return 0;
}

构造函数在初始化时,会先走初始化列表进行初始化,若初始化列表没有初始化,再走构造函数内部看是否初始化,若都没有,就只能要看编译器是否初始化,但一般都为随机值。

一般的内置类型的成员普通的构造函数就可以实现,不需要初始化列表。但有些成员变量只能通过初始化列表进行初始化。

前面说过,初始化列表可以认为是每个成员变量定义初始化的地方,而有些变量只能在定义的时候进行初始化,如:

// const常量只能在定义时初始化一次
const int a = 1;
//引用也只能在初始化时定义
int x = 10;
int& y = x;

还有一个,没有默认构造的类类型变量。如:

该默认构造无需传参,其初始化时若无参数,则会使用缺省值,故可完成初始化。但如果没有缺省值,则程序会编译出错。

#include<iostream>class A
{
public:A(int a):_a(a){std::cout << "A()" << std::endl;}private:int _a;
};class Date
{
public:Date(int& xx, int year = 1, int month = 1, int day = 1):_year(year), _month(month),_day(day),a(1),x(xx){}void Print(){std::cout << _year << "/" << _month << "/" << _day << std::endl;}private:int _year;int _month;int _day;const int a;int& x;A y;
};int main()
{int x = 1;Date d1(x, 2024, 7, 20);return 0;
}

其编译会报错

这里必须要传入参数,所以我们就需要在初始化列表进行初始化。

#include<iostream>class A
{
public:A(int a):_a(a){std::cout << "A()" << std::endl;}private:int _a;
};class Date
{
public:Date(int& xx, int year = 1, int month = 1, int day = 1):_year(year), _month(month),_day(day),a(1),x(xx),y(1){}void Print(){std::cout << _year << "/" << _month << "/" << _day << std::endl;}private:int _year;int _month;int _day;const int a;int& x;A y;
};int main()
{int x = 1;Date d1(x, 2024, 7, 20);return 0;
}

此外,C++11⽀持在成员变量声明的位置给缺省值,这个缺省值主要是给没有显示在初始化列表初始化的成员使⽤的。

#include<iostream>class A
{
public:A(int a):_a(a){std::cout << "A()" << std::endl;}private:int _a;
};class Date
{
public:Date(int& xx, int year = 1, int month = 1, int day = 1):_year(year), _month(month),_day(day),x(xx){}void Print(){std::cout << _year << "/" << _month << "/" << _day << std::endl;}private:int _year;int _month;int _day;const int a = 1;int& x;A y = 1;
};int main()
{int x = 1;Date d1(x, 2024, 7, 20);return 0;
}

但尽量使⽤初始化列表初始化,因为那些你不在初始化列表初始化的成员也会⾛初始化列表,如果这 个成员在声明位置给了缺省值,初始化列表会用这个缺省值初始化。

但如果没有给缺省值,对于没有显示在初始化列表初始化的内置类型成员是否初始化取决于编译器,C++并没有规定。对于没有显示在初始化列表初始化的自定义类型成员会调用这个成员类型的默认构造函数,如果没有默认构造会编译错误。所以尽量使用初始化列表。


类型转换

举最简单的例子来说:

#include<iostream>int main()
{int a = 10;double b = a;return 0;
}

这是一个简单的类型转换。

C++⽀持内置类型隐式类型转换为类类型对象,但需要有相关内置类型为参数的构造函数。

#include<iostream>class A
{
public://构造函数A(int a){_a = a;}void Print(){std::cout << _a  << std::endl;}
private:int _a;
};int main()
{// 6构造⼀个A的临时对象,再用这个临时对象拷贝构造a1// 但若编译器遇到连续构造+拷贝构造就会优化为直接构造A a1 = 6;a1.Print();//这个隐式类型转换过程为://构造函数A a2(1);//拷贝构造,注:该类只有内置类型的成员变量,编译器自动生成的拷贝构造就能实现目的A a3 = a2;//所以就直接通过隐式类型转换来使用return 0;
}

在C++11之前,其是不支持多参数转化,一些较老的编译器就不支持多参数转化。

#include<iostream>class A
{
public://构造函数A(int a1 = 1, int a2 = 2){_a1 = a1;_a2 = a2;}void Print(){std::cout << _a1 << " " << _a2 << std::endl;}private:int _a1;int _a2;
};int main()
{A a = { 6,66 };a.Print();//相当于:A a1(1, 11);A a2 = a1;a2.Print();return 0;
}

构造函数前⾯加关键字 explicit 就可以不再⽀持隐式类型转换。


static成员

⽤static修饰的成员变量,称之为静态成员变量,静态成员变量⼀定要在类外进⾏初始化。其为所有类对象所共享,不属于某个具体的对象,不存在对象中,存放在静态区。

#include<iostream>class A
{
public:private:int a;static int b;
};//在类外初始化静态成员变量
int A::b = 1;int main()
{return 0;
}

而⽤static修饰的成员函数,称之为静态成员函数,静态成员函数是没有this指针的。静态成员函数可以访问其他的静态成员,但是不能访问⾮静态的,因为没有this指针。但⾮静态的成员函数,可以访问任意的静态成员变量和静态成员函数。

#include<iostream>class A
{
public:static int Get(){return b;}void func(){std::cout << a << ' ' << b << std::endl;}private:int a = 1;static int b;
};//在类外初始化静态成员变量
int A::b = 1;int main()
{A a;a.func();return 0;
}

一定要注意,静态成员变量不能在声明位置给缺省值初始化,因为缺省值是个构造函数初始化列表的,静态成员变量不属于某个对象,不⾛构造函数初始化列表。

由于静态成员也是类的成员,所以其受public、protected、private等访问限定符和类域的限制。

相关文章:

类和对象(四)

构造函数中的初始化列表 之前在实现构造函数时&#xff0c;主要是在函数体内进行赋值&#xff0c;而构造函数还有另一种初始化方式&#xff0c;通过初始化列表进行初始化。 初始化列表的使⽤⽅式是以⼀个冒号开始&#xff0c;接着是⼀个以逗号分隔的数据成员列表&#xff0c;…...

<PLC><HMI><汇川>在汇川HMI画面中,如何为UI设置全局样式?

前言 汇川的HMI软件是使用了Qt来编写的,因此在汇川的HMI程序编写过程,是支持使用qt的样式来自定义部件样式的,即qss格式。 概述 汇川的软件本身提供三个系统的style样式,我们可以直接使用,但是,如果系统提供的样式不符合你的需求,那么你可以对其进行修改,或者自己新建…...

在Git项目中添加并应用“.gitignore”文件

在Git项目中添加并应用.gitignore文件 创建或修改.gitignore文件&#xff1a; 在项目的根目录下创建一个名为.gitignore的文件。如果已经有此文件&#xff0c;可以直接修改。 在文件中添加您希望Git忽略的文件和目录。例如&#xff1a; # 忽略所有的log文件 *.log# 忽略所有的…...

LeetCode Hot100 搜索二维矩阵

给你一个满足下述两条属性的 m x n 整数矩阵&#xff1a; 每行中的整数从左到右按非严格递增顺序排列。每行的第一个整数大于前一行的最后一个整数。 给你一个整数 target &#xff0c;如果 target 在矩阵中&#xff0c;返回 true &#xff1b;否则&#xff0c;返回 false 。…...

iOS中的KVO(Key-Value Observing)详解

iOS中的KVO&#xff08;Key-Value Observing&#xff09;详解 一、KVO概述 KVO&#xff08;Key-Value Observing&#xff09;&#xff0c;即键值观察/监听&#xff0c;是苹果提供的一套事件通知机制。它允许一个对象&#xff08;观察者&#xff09;观察/监听另一个对象&#…...

算法 —— 暴力枚举

目录 循环枚举 P2241 统计方形&#xff08;数据加强版&#xff09; P2089 烤鸡 P1618 三连击&#xff08;升级版&#xff09; 子集枚举 P1036 [NOIP2002 普及组] 选数 P1157 组合的输出 排列枚举 P1706 全排列问题 P1088 [NOIP2004 普及组] 火星人 循环枚举 顾名思…...

构造+有序集合,CF 1023D - Array Restoration

一、题目 1、题目描述 2、输入输出 2.1输入 2.2输出 3、原题链接 1023D - Array Restoration 二、解题报告 1、思路分析 先考虑合法性检查&#xff1a; 对于数字x&#xff0c;其最左位置和最右位置 之间如果存在数字比x小&#xff0c;则非法 由于q次操作&#xff0c;第q…...

Scrapy 爬取旅游景点相关数据(四)

本节内容主要为&#xff1a; &#xff08;1&#xff09;创建数据库 &#xff08;2&#xff09;创建数据库表 &#xff08;3&#xff09;爬取数据进MYSQL库 1 新建数据库 使用MYSQL数据库存储数据&#xff0c;创建一个新的数据库 create database scrapy_demo;2 新建数据表 CR…...

Vue常用指令及其生命周期

作者&#xff1a;CSDN-PleaSure乐事 欢迎大家阅读我的博客 希望大家喜欢 目录 1.常用指令 1.1 v-bind 1.2 v-model 注意事项 1.3 v-on 注意事项 1.4 v-if / v-else-if / v-else 1.5 v-show 1.6 v-for 无索引 有索引 生命周期 定义 流程 1.常用指令 Vue当中的指令…...

简化数据流:Apache SeaTunnel实现多表同步的高效指南

Apache SeaTunnel除了单表之间的数据同步之外&#xff0c;也支持单表同步到多表&#xff0c;多表同步到单表&#xff0c;以及多表同步到多表&#xff0c;下面简单举例说明如何实现这些功能。 单表 to 单表 一个source&#xff0c;一个sink。 从mysql同步到mysql&#xff0c;…...

均匀圆形阵列原理及MATLAB仿真

均匀圆形阵列原理及MATLAB仿真 目录 前言 一、均匀圆阵原理 二、圆心不存在阵元方向图仿真 三、圆心存在阵元方向图仿真 四、MATLAB仿真代码 总结 前言 本文详细推导了均匀圆形阵列的方向图函数&#xff0c;对圆心不放置阵元和圆心放置阵元的均匀圆形阵列方向图都进行了仿…...

vue2使用univerjs

1、univerjs Univer 提供了一个全面的企业级文档与数据协同的解决方案&#xff0c;支持电子表格、文本文档和演示幻灯片三大核心文档类型。通过灵活的 API 和插件机制&#xff0c;开发者可以在 Univer 的基础上进行个性化功能的定制和扩展&#xff0c;以适应不同用户在不同场景…...

VUE3 el-table-column header新增必填*

1.在需要加必填星号的el-table-column上添加render-header属性 <el-table-column :label"getName(产品代码)" :render-header"addRedStart" prop"MODELCODE" min-width“4.5%”> <template v-slot"scope"> <el-input …...

条件概率和贝叶斯公式

...

Kali中docker与docker-compose的配置

权限升级 sudo su 升级为root用户 更新软件 apt-get update安装HTTPS协议和CA证书 apt-get install -y apt-transport-https ca-certificates下载docker apt下载docker apt install docker.io 验证docker安装是否成功 查版本 docker -v 启动docker systemctl start …...

C++ | Leetcode C++题解之第283题移动零

题目&#xff1a; 题解&#xff1a; class Solution { public:void moveZeroes(vector<int>& nums) {int n nums.size(), left 0, right 0;while (right < n) {if (nums[right]) {swap(nums[left], nums[right]);left;}right;}} };...

Exponential Moving Average (EMA) in Stable Diffusion

1.Moving Average in Stable Diffusion (SMA&EMA) 1.Moving average 2.移动平均值 3.How We Trained Stable Diffusion for Less than $50k (Part 3) Moving Average 在统计学中&#xff0c;移动平均是通过创建整个数据集中不同选择的一系列平均值来分析数据点的计算。 …...

017、Vue动态tag标签

文章目录 1、先看效果2、代码 1、先看效果 2、代码 <template><div class "tags"><el-tag size"medium"closable v-for"item,index in tags":key"item.path":effect"item.title$route.name?dark:plain"cl…...

RocketMQ 架构概览

Apache RocketMQ 是一个分布式消息中间件和流计算平台&#xff0c;提供低延迟、高性能和可靠的队列服务&#xff0c;并且支持大规模的分布式系统。在详细介绍 RocketMQ 的整体架构之前&#xff0c;先了解其设计目标和核心特性是很重要的。RocketMQ 主要用于处理大规模的消息&am…...

优化医疗数据管理:Kettle ETL 数据采集方案详解

在现代医疗保健领域&#xff0c;数据的准确性、完整性和及时性对于提高医疗服务质量和患者护理至关重要。为了有效管理和利用医疗数据&#xff0c;Kettle ETL&#xff08;Extract, Transform, Load&#xff09;数据采集方案成为了许多医疗机构的首选工具之一。本文将深入探讨Ke…...

浏览器访问 AWS ECS 上部署的 Docker 容器(监听 80 端口)

✅ 一、ECS 服务配置 Dockerfile 确保监听 80 端口 EXPOSE 80 CMD ["nginx", "-g", "daemon off;"]或 EXPOSE 80 CMD ["python3", "-m", "http.server", "80"]任务定义&#xff08;Task Definition&…...

JavaSec-RCE

简介 RCE(Remote Code Execution)&#xff0c;可以分为:命令注入(Command Injection)、代码注入(Code Injection) 代码注入 1.漏洞场景&#xff1a;Groovy代码注入 Groovy是一种基于JVM的动态语言&#xff0c;语法简洁&#xff0c;支持闭包、动态类型和Java互操作性&#xff0c…...

《Qt C++ 与 OpenCV:解锁视频播放程序设计的奥秘》

引言:探索视频播放程序设计之旅 在当今数字化时代,多媒体应用已渗透到我们生活的方方面面,从日常的视频娱乐到专业的视频监控、视频会议系统,视频播放程序作为多媒体应用的核心组成部分,扮演着至关重要的角色。无论是在个人电脑、移动设备还是智能电视等平台上,用户都期望…...

全球首个30米分辨率湿地数据集(2000—2022)

数据简介 今天我们分享的数据是全球30米分辨率湿地数据集&#xff0c;包含8种湿地亚类&#xff0c;该数据以0.5X0.5的瓦片存储&#xff0c;我们整理了所有属于中国的瓦片名称与其对应省份&#xff0c;方便大家研究使用。 该数据集作为全球首个30米分辨率、覆盖2000–2022年时间…...

【快手拥抱开源】通过快手团队开源的 KwaiCoder-AutoThink-preview 解锁大语言模型的潜力

引言&#xff1a; 在人工智能快速发展的浪潮中&#xff0c;快手Kwaipilot团队推出的 KwaiCoder-AutoThink-preview 具有里程碑意义——这是首个公开的AutoThink大语言模型&#xff08;LLM&#xff09;。该模型代表着该领域的重大突破&#xff0c;通过独特方式融合思考与非思考…...

安卓基础(aar)

重新设置java21的环境&#xff0c;临时设置 $env:JAVA_HOME "D:\Android Studio\jbr" 查看当前环境变量 JAVA_HOME 的值 echo $env:JAVA_HOME 构建ARR文件 ./gradlew :private-lib:assembleRelease 目录是这样的&#xff1a; MyApp/ ├── app/ …...

Spring是如何解决Bean的循环依赖:三级缓存机制

1、什么是 Bean 的循环依赖 在 Spring框架中,Bean 的循环依赖是指多个 Bean 之间‌互相持有对方引用‌,形成闭环依赖关系的现象。 多个 Bean 的依赖关系构成环形链路,例如: 双向依赖:Bean A 依赖 Bean B,同时 Bean B 也依赖 Bean A(A↔B)。链条循环: Bean A → Bean…...

DingDing机器人群消息推送

文章目录 1 新建机器人2 API文档说明3 代码编写 1 新建机器人 点击群设置 下滑到群管理的机器人&#xff0c;点击进入 添加机器人 选择自定义Webhook服务 点击添加 设置安全设置&#xff0c;详见说明文档 成功后&#xff0c;记录Webhook 2 API文档说明 点击设置说明 查看自…...

如何更改默认 Crontab 编辑器 ?

在 Linux 领域中&#xff0c;crontab 是您可能经常遇到的一个术语。这个实用程序在类 unix 操作系统上可用&#xff0c;用于调度在预定义时间和间隔自动执行的任务。这对管理员和高级用户非常有益&#xff0c;允许他们自动执行各种系统任务。 编辑 Crontab 文件通常使用文本编…...

MySQL 索引底层结构揭秘:B-Tree 与 B+Tree 的区别与应用

文章目录 一、背景知识&#xff1a;什么是 B-Tree 和 BTree&#xff1f; B-Tree&#xff08;平衡多路查找树&#xff09; BTree&#xff08;B-Tree 的变种&#xff09; 二、结构对比&#xff1a;一张图看懂 三、为什么 MySQL InnoDB 选择 BTree&#xff1f; 1. 范围查询更快 2…...