本篇博客让我们来见识一下C++中新增的类型转换方法
[TOC]
1.C语言中类型转换
在C语言中,类型转换有下面两种形式
- 隐式类型转换
- 显示强制类型转换
int a=(int)'c'
这两种方式想必各位都很熟悉了,但隐式类型转换在一些场景里面会出现问题
1 | void insert(size_t pos,char c) |
上面的代码中,end是int类型,当进行比较的时候,end会-1直到小于pos
如果pos=0
,问题就来了!
隐式类型转换会让end在比较的时候被转换为size_t
无符号整型,而在无符号整型中,-1
是一个非常大的正数,从而导致这个函数进入死循环!
- 隐式类型转换可能会丢失数据的精度
- 显示类型转换的写法都一样,导致不能很好的区分情况
C++委员会也是认识到了这里的问题,当产生隐式类型转换的时候,难以跟踪错误的来源,于是开发了下面的新的类型转换方式
不过,因为C++兼容C语言,所以C中的转换方式依旧支持
2.C++中的强制类型转换
C++中新增了下面四种明明的强制类型转换操作符
1 | static_cast、reinterpret_cast、const_cast、dynamic_cast |
2.1 static_cast
这个关键字是用于相近类型之间的转换的,比如double和int,char和int之间
1 | double d = 11.4; |
2.2 reinterpret_cast
这个关键字用于不相近类型之间的转换,比如指针转成int
1 | int* p = &a1; |
打印的结果如下(每次运行都不一样)
1 | 2029408 |
2.3 const_cast
如同其名,这个关键字的作用是取消一个变量的const属性
1 | const int c1 = 3;//这里定义的变量是在栈上的,可以间接修改 |
欸,为什么我们取地址之后,修改为4了,变量c1本身不会变化呢?
这是因为编译器做了一些优化,把c1放到了某个地方,取的时候并没有直接去内存里面取
volatile关键字
这里我们可以使用volatile
关键字修饰变量,要求每一次都必须要去内存中取
1 | //volatile关键字,每次访问c都去内存中取,屏蔽编译器优化 |
2.4 dynamic_cast
该关键字是用于继承中,将一个父类的指针/引用
转换为子类对象的指针/引用
之前学习继承的时候,我们了解过
- 向上转型:父类的指针、引用可以直接指向子类对象的指针/引用(这是一个赋值兼容的规则,不需要进行转换)
- 向下转型:反过来之后,可以直接赋值吗?不够安全
dynamic_cast
的作用就是判断一个父类指针指向的是不是他的子类
- 如果是,能够成功转换
- 不能则返回0
这个关键字最大的作用,便是可以帮我们判断这个父类指针/引用指向的是否为一个子类对象
1 | class A |
这里有个要求,那便是父类中必须要有虚函数(多态),否则无法成功转换
3.C++强制类型转换的作用
C++希望我们规范强制类型转换的情景,针对性的调用不同的关键字
但是由于它没有强制,在实际情况中用的反而不多
不过需要注意的是,强制类型转换会关闭/挂起正常的类型检查,在强制类型转换之前,我们要仔细检查是否还有别的方法来达到目的。最好是避免使用强制类型转换!
4.RTTI
之前学习智能指针的时候,我们学过一种思路叫RAII
这里的RTTI
全称为Run-time Type identification
,即运行时类型识别
C++通过下面几种方式来支持RTTI:
- typeid
- decltype
- dyanmic_cast
这个概念只需要了解即可!
- 本文标题:【C++】类型转换方法
- 创建时间:2022-10-20 13:40:46
- 本文链接:posts/3134809219/
- 版权声明:本博客所有文章除特别声明外,均采用 BY-NC-SA 许可协议。转载请注明出处!