《C++的类型转换》

目录

一、c语言中的类型转换

1、隐式类型转化:

2、强制类型转化:

3、缺点

二、c++新的类型转换

1、内置类型转为自定义类型

3、自定义类型转换为内置类型

三、C++的规范的强制类型转换

1、C++新增四种规范的类型转换的原因

2、static_cast

3、reinterpret_cast

4、const_cast

5、dynamic_cast

6、警惕强制转化

结束语


前言

        本篇文章来介绍C++11基于C语言对于类型转换变化的介绍,介绍类型转换的新增内容,内容干货满满,看这一篇包学会

一、c语言中的类型转换

        在C语言中,如果赋值运算符左右两侧类型不同,或者形参与实参类型不匹配,或者返回值类型与接收返回值类型不一致时,就需要发生类型转化,C语言中总共有两种形式的类型转换:隐式类型转换显式强制类型转换

1、隐式类型转化:

        编译器在编译阶段自动进行,能转就转,不能转就编译失败。

        通常发生在整形之间,整形和浮点数之间。bool和整形之间, bool和指针之间(利用指针是否为空指针做判断时存在隐式转换),如下图举例

其他场景介绍:

        下图比较的时候end会隐式类型转换成size_t,再比较

2、强制类型转化:

        一般用于指针转换,需要用户自己处理,显示的转换类型如下图(存在截断风险)所示

特别注意只有类型之间有一定关联的时候才会发生类型转换,毫不相干的两个类型不能发生转换

如下图所示,无法将一个指针转换为double类型变量:

3、缺点

        转换的可视性比较差,所有的转换形式都是以一种相同形式书写,难以跟踪错误的转换


二、c++新的类型转换

        c++是面向对象的语言,c++语言带来了自定义类型的对象,为类型的家族注入新鲜新鲜血液的同时,也带来了内置类型与自定义类型之间互相转换的问题

1、内置类型转为自定义类型

        定义类的时增添对应参数的构造,直接调用构造对象,内置类型作为传参构造为对应的自定义类型的对象。

2、自定义类型转换为自定义类型

        对于这种转换,我们也是只需要定义类的时增添对应参数的构造就可以实现对应的类型转化(调用参数与被转换类型匹配的构造函数)。

        联系到STL库中,某一个容器可以使用{ }进行多个元素初始化的原理,就实现了自定义类型及内置类型向自定义类型的一个转换,{ }中的多个内置类型,先转换为多个容器中的单位元素类型(内置类型转自定义类型对象);所有转换过来的的元素构造为initializer_list对象,最终利用initializer_list转换为对应的容器类型对象(构造函数支持自定义转自定义类型对象)。具体的原理实现大家可以参考博客《C++11实用方法介绍(一)》中的讲解,更深层次的理解。

特别注意:

        在继承与多态当中,基类对象可以赋值给基类变量,好像是两个自定义类型之间的转换,但这不是类型转化,这是切片操作,这万万不可混为一谈!!!

3、自定义类型转换为内置类型

        这种情况看起来很奇怪,内置类型可以转换为自定义类型是因为有对应的构造函数支持,而内置类型都是写好的,我们无法为其增添支持操作的构造函数,拿又该怎么办呢?

        本质要重载一个operator类型 隐式类型转换 如:下面的A

        由于隐式转换(C语言的沉重历史包袱)的存在,迫于无奈只能特殊处理,operator +类型,不需要有返回值


三、C++的规范的强制类型转换

1、C++新增四种规范的类型转换的原因

C风格的转换格式很简单,但是有不少缺点

        1. 隐式类型转化有些情况下可能会出问题:比如数据精度丢失

        2. 显式类型转换将所有情况混合在一起,代码不够清晰

        因此C++提出了自己的类型转化风格,注意因为C++要兼容C语言,所以C++中还可以使用C语言的转化风格。

即非必须实用C++11规范化类型转换(保证以前的代码仍然可以用),但最好是规范!!!(很多大型公司强制要求,要有好的代码编写习惯)

2、static_cast<T>

        用于非多态类型的转换(静态转换),编译器隐式执行的任何类型转换都可用static_cast,但它不能用于两个不相关的类型进行转换.

等同于以前的隐式类型转换

下图为使用举例(double->int)

3、reinterpret_cast<T>

        通常为操作数的位模式提供较低层次的重新解释,用于将一种类型转换为另一种不同的类型

        等同于以前的强制类型转换(有一方为指针转换)

        下图为使用举例(int->int*)

4、const_cast<T>

        最常用的用途就是删除变量的const属性,方便赋值

Q:这也是强制类型转换,但是为什么要把去掉const属性单独拿出来做一个类型转换操作符?

(1)原来去除const类型的方式

        我们预估a1的值已经被改变为3,可是结果表示并没有更改,结果与预想并不对应。难道真的是我们的a1数值没有改变吗?让我们来看一下监视窗口:

        我们发现此时a1的数值确实被改为了3,但为什么仍然直接打印a1时会不对。这个时候我们就要补充一些知识:编译器看到const类型的变量,会将变量扔到寄存器(增加访问效率),我们这里更改其数值,更改的是它在内存中存储的数值,寄存器中的没有改动,输出时输出的是寄存器中没有改动过的变量。故而这里出现错误。

        去掉const属性是有一些内存可见优化的的风险,通过在定义const变量前添加volatile修饰符,表明此数据不存入寄存器来解决。

2、使用关键字规范化去除

        这里就是专门提醒去掉const属性是有一些内存可见优化的的风险,要注意是否加了volatile,这也回答了上面提出的问题

5、dynamic_cast<T>

        用于将一个父类对象的指针/引用转换为子类对象的指针或引用(动态转换)

向上转型:子类对象指针/引用->父类指针/引用(不需要转换,赋值兼容规则)

向下转型:父类对象指针/引用->子类指针/引用(用dynamic_cast转型是安全的)

我们给定一个基类,一个子类,以及参数为基类指针的函数(举例):

由于函数参数为基类的指针,它既可以指向基类对象,也可以指向子类对象

(1)、pa指向子类对象,转回子类,是安全的,正常转换

(2)、pa指向父类对象(基类可能没有子类新加的成员),转回子类,是不安全的,存在越界的风险问题,转换失败

利用dynamic_cast会先检查是否能转换成功,能成功则转换,不能则返回

注意:

1. dynamic_cast只能用于父类含有虚函数的类

2. dynamic_cast会先检查是否能转换成功,能成功则转换,不能则返回

6、警惕强制转化

        强制类型转换关闭或挂起了正常的类型检查,每次使用强制类型转换前,程序员应该仔细考虑是否还有其他不同的方法达到同一目的,如果非强制类型转换不可,则应限制强制转换值的作用域,以减少发生错误的机会。强烈建议:避免使用强制类型转换!!!!


结束语

        本篇文章的内容就到此结束了,对于c++11的类型转化的介绍也来到尾声,希望大家能有所收获,能够应用自如,如果有什么内容不明白的,大家可以在评论去向我提问,我会一一回答,当然有什么错误或者有什么不足的地方,希望大家可以包容并指出。希望大家可以持续关注之后内容,最后向每一位读者送上真诚的小花。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mfbz.cn/a/579807.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

头歌实践教学平台:CG5-v1.0-简单光照效果

第2关&#xff1a;OpenGL球体镜面反射 一.任务描述 根据提示&#xff0c;在右侧修改代码&#xff0c;并自己绘制出图形。平台会对你编写的代码进行测试。 1.本关任务 为在场景中增加光照&#xff0c;需要执行以下步骤。 (1).设置一个或多个光源&#xff0c;设定它的有关属性…

信息系统项目管理师0074:数据集成(5信息系统工程—5.3系统集成—5.3.3数据集成)

点击查看专栏目录 文章目录 5.3.3数据集成1.数据集成层次2.异构数据集成5.3.3数据集成 数据集成的目的是运用一定的技术手段将系统中的数据按一定的规则组织成为一个整体,使得用户能有效地对数据进行操作。数据集成处理的主要对象是系统中各种异构数据库中的数据。数据仓库技术…

eclipse导入工程提示Project has no explicit encoding set

eclipse导入工程提示Project has no explicit encoding set 文章目录 eclipse导入工程提示Project has no explicit encoding set一、Eclipse的工程导入二、可能的问题1.在工程名下有黄色叹号 一、Eclipse的工程导入 用Eclipse的导入可以将原有工程导入到新环境中 具体方法是&…

1. 房屋租赁管理系统(基于springboot/vue的Java项目)

1.此系统的受众 1.1 在校学习的学生&#xff0c;可用于日常学习使用或是毕业设计使用 1.2 毕业一到两年的开发人员&#xff0c;用于锻炼自己的独立功能模块设计能力&#xff0c;增强代码编写能力。 1.3 亦可以部署为商化项目使用。 2. 技术栈 jdk8springbootvue2mysq5.7&8…

区块链与Web3.0:区块链项目的推广

数字信息时代&#xff0c;一场革命正在酝酿中&#xff0c;那就是区块链与Web3.0的结合。这种结合将会改变我们对于信息传输、存储和使用的方式&#xff0c;并有可能推动媒体行业向新的高度发展。这种转变不仅关系到我们如何获取和使用信息&#xff0c;也涉及到如何用创新的方式…

四、OSPF域间路由

注&#xff1a;区域&#xff08;area&#xff09;是以接口进行划分的 描述&#xff1a; R1的g0/0/1接口属于area 0 √ R1属于区域0和区域1 1.设计原则 1、OSPF区域的设计原则&#xff1a; 骨干区域有且只能存在一个 非骨干区域必须和骨干区域相连 多区域时&#…

VulnHub靶机 DC-9 靶机 详细渗透过程

VulnHub靶机 DC-9 打靶实战 详细渗透过程 目录 VulnHub靶机 DC-9 打靶实战 详细渗透过程一、将靶机配置导入到虚拟机当中二、渗透测试主机发现端口扫描Web渗透SQL注入登入后台文件包含SSH爆破提权 一、将靶机配置导入到虚拟机当中 靶机地址&#xff1a; https://www.vulnhub.…

【MHA】MySQL高可用MHA介绍1-功能,架构,优势,案例

目录 一 MHA 介绍 1 MHA功能 自动化主服务器监控和故障转移 交互式&#xff08;手动启动的&#xff09;主故障转移 非交互式主故障转移 在线切换主机 2 主服务器故障转移的难点 二 MHA架构 1 MHA组件 2 自定义扩展&#xff08;脚本&#xff09; 三 MHA优势 1 MHA可以…

锂电池SOH预测 | 基于BP神经网络的锂电池SOH预测(附matlab完整源码)

锂电池SOH预测 锂电池SOH预测完整代码锂电池SOH预测 锂电池的SOH(状态健康度)预测是一项重要的任务,它可以帮助确定电池的健康状况和剩余寿命,从而优化电池的使用和维护策略。 SOH预测可以通过多种方法实现,其中一些常用的方法包括: 容量衰减法:通过监测电池的容量衰减…

jupyter notebook设置代码自动补全

jupyter notebook设置代码自动补全 Anaconda Prompt窗口执行 pip install jupyter_contrib_nbextensionsjupyter contrib nbextensions install --userpip install jupyter_nbextensions_configuratorjupyter nbextensions_configurator enable --user按如下图片设置 卸载jed…

HarmonyOS Next从入门到精通实战精品课

第一阶段&#xff1a;HarmonyOS Next星河版从入门到精通该阶段由HarmonyOS Next星河版本出发&#xff0c;介绍HarmonyOS Next版本应用开发基础概念&#xff0c;辅助学员快速上手新版本开发范式&#xff0c;共计42课时 第一天鸿蒙NEXT Mac版、Windows版【编辑器】和【模拟器】&a…

长度最小的子数组 ---- 滑动窗口

题目链接 题目: 分析: 解法一:暴力解法, 找到所有连续子数组, 保留满足条件的解法二: 利用滑动窗口 找子数组 因为数组中都是正整数, 通过进窗口的操作, 我们找到一组, 如示例一中的2,3,1,2, 判断满足和>7, 那么根据单调性, 我们就不再需要判断加上后面两个数的两个子数组…

记录浏览器打开网站拦截提示不安全解决方法

浏览器可能会因为多种原因显示“不安全”的警告,这通常是由于安全设置不当或配置错误造成的。以下是一些常见的原因和解决方法: 1. HTTPS未启用 原因:如果网站使用HTTP而不是HTTPS,浏览器可能会显示不安全的警告。 解决方法:配置SSL/TLS证书并使用HTTPS来加密数据传输…

鹏哥C语言复习——字符函数与字符串函数

目录 一.字符函数 1.字符分类函数 2.字符转换函数 二.基础字符串函数 1.strlen函数 2.strcpy函数 3.strcat函数 4.strcmp函数 三.基础字符串函数优化 1.strncpy函数 2.strncat函数 3.strncmp函数 四.进阶字符串函数 1.strstr函数 2.strtok函数 3.strerror函数 一…

做大模型产品,如何设计prompt?

做GenAI产品&#xff0c;除了要设计好的AI任务流程&#xff0c;合理的拆分业务以外&#xff0c;最重要的就是写好prompt&#xff0c;管理好prompt&#xff0c;持续迭代prompt。 prompt一般有两种形式&#xff1a;结构化prompt和对话式prompt。 结构化prompt的优点是通过规范的…

vim的IDE进阶之路

一 ctags 1 安装 安装ctags比较简单&#xff0c;我用的是vim-plug&#xff0c;网络上随便一搜应该就有很多教程&#xff0c;而且没有什么坑 2 使用 vim之函数跳转功能_nvim函数跳转-CSDN博客https://blog.csdn.net/ballack_linux/article/details/71036072不过针对cuda程序…

【Android】 四大组件详解之广播接收器、内容提供器

目录 前言广播机制简介系统广播动态注册实现监听网络变化静态注册实现开机自启动 自定义广播发送标准广播发送有序广播 本地广播 内容提供器简介运行时权限访问其他程序中的数据ContentResolver的基本用法读取系统联系人 创建自己的内容提供器创建内容提供器的步骤 跨程序数据共…

数据仓库是什么

写在前面 刚接触大数据的新手小白可能会对数据仓库这个词比较陌生&#xff0c;本文将介绍数据仓库的主要特征及OLTP&OLAP的区别&#xff0c;帮助读者更好理解数据仓库。 一、什么是数据仓库 数据仓库&#xff0c;简称数仓&#xff0c;是一个对数据进行加工&#xff0c;集…

【go零基础】go-zero从零基础学习到实战教程 - 0环境配置

是个前端&#xff0c;最近开始学习go&#xff0c;后端除node外基本0基础&#xff0c;所以学习曲线有点绕&#xff0c;目标是个基础的服务端demo&#xff0c;搞个api服务后台&#xff0c;包含基础的用户登录、文章发布和写文章、权限控制&#xff0c;差不多就是个完整博客系统。…

CentOS 9 (stream) 安装 nginx

1.我们直接使用安装命令 dnf install nginx 2.安装完成后启动nginx服务 # 启动 systemctl start nginx # 设置开机自启动 systemctl enable nginx# 重启 systemctl restart nginx# 查看状态 systemctl status nginx# 停止服务 systemctl stop nginx 3.查看版本确认安装成功…
最新文章