注:原创不易,转载请务必注明原作者和出处,感谢支持!

注:内容来自某培训课程,不一定完全正确!

一 类型转换

类型转换的含义是通过改变一个变量的类型为别的类型从而改变变量的表示方式。C++提供了4种类型转换操作符来应对不同场合的类型转换。

语法 适用场景
static_cast 一般的转换(比如C++内建类型之间的转换)
dynamic_cast 通常在基类和派生类之间转换时使用
const_cast 主要针对const的转换
reinterpret_cast 用于进行没有任何关联之间的转换,比如一个字符指针转换为一个整型数



总结:

(1)static_cast用于内置数据类型,具有继承关系的指针或者引用的转换。

(2)dynamic_cast只能转换具有继承关系的指针或者引用,并且只能由子类型转成父类型(基类型)。在具有基础关系的指针或者引用的转换上,相较于static_cast,dynamic_cast,添加了额外的安全检查,拒绝了类型不安全的转换,更加地安全。

(3)const_cast用来给基础数据类型,指针或者引用“加上”或者“去除”const

(4)reinterpret_cast用于任意两个无关类型的指针或者引用的转换

有关C++类型转换的一个详细案例如下所示。


class Building {};
class Animal {};
class Cat : public Animal {}; void Test1()
{
// static_cast
int a = 65;
char c = static_cast<char>(a);
cout << c << endl; // 基础数据类型的指针 - 无法转换
// int *p = nullptr;
// char *sp = static_cast<char *>(p); // 对象指针 - 无法转换
// Building *building = nullptr;
// Animal *ani = static_cast<Animal *>(building); // 转换具有基础关系的对象指针
// 父类指针转子类指针
Animal *ani = nullptr;
Cat *cat = static_cast<Cat *>(ani);
// 子类指针转父类指针
Cat *soncat = nullptr;
Animal *anifather = static_cast<Animal *>(soncat);
// 父类引用转子类引用
Animal aniobj;
Animal &aniref = aniobj;
Cat &catref = static_cast<Cat &>(aniref);
// 子类引用转父类引用
Cat catobj;
Cat &catref2 = catobj;
Animal & aniref2 = static_cast<Animal &>(catref2); // 总结:static_cast用于内置数据类型,具有继承关系的指针或者引用的转换
} void Test2()
{
// dynamic_cast只能转换具有继承关系的指针或者引用
// 其在转换之前会进行对象类型的检查 // 内建数据类型的转换 - 无法转换
// dynamic_cast中的类型必须是指向完整类类型或者void *的指针或者引用
// int a = 10;
// char c = dynamic_cast<char>(a); // 非继承关系的指针的转换 - 无法转换,两者不具备继承关系
// Animal *pani = nullptr;
// Building *pbuilding = dynamic_cast<Building *>(pani); // 具有继承关系的指针 - 无法转换,父类指针转子类指针是类型不安全的
// Animal *pani = nullptr;
// Cat *pcat = dynamic_cast<Cat *>(pani); // 具有继承关系的指针 - 可以转换,子类指针转换为父类指针是类型安全的
Cat *pcat = nullptr;
Animal *pani = dynamic_cast<Animal *>(pcat); // 具有基础关系的引用 - 无法转换,原因同样是父类引用转换成子类引用是类型不安全的
// Animal aniobj;
// Animal &aniref = aniobj;
// Cat &catref = dynamic_cast<Cat &>(aniref); // 具有继承关系的引用 - 可以转换,子类引用转父类引用是类型安全的
Cat catobj;
Cat &catref = catobj;
Animal &aniref = dynamic_cast<Animal &>(catref); // 总结:dynamic_cast只能转换具有继承关系的指针或者引用
// 并且只能由子类型转成父类型(基类型)
// 在具有基础关系的指针或者引用的转换上,相较于static_cast,dynamic_cast
// 添加了额外的安全检查,拒绝了类型不安全的转换,更加地安全
} void Test3()
{
// 基础数据类型
int a = 10;
const int &b = a;
// b = 20; b为const引用,无法通过b来修改a的值
// 通过const_cast去除const
int &c = const_cast<int &>(b);
// 通过引用c来修改a的值
c = 20;
// a值为20现在
cout << "a = " << a << endl; // 指针
// 去除const
const int *p1 = nullptr;
int *p2 = const_cast<int *>(p1); // 加上const
int *p3 = nullptr;
const int *p4 = const_cast<const int *>(p3); // 引用 - 去除const
int k = 20;
const int &r1 = k;
int &r2 = const_cast<int &>(r1); // 引用 - 加上const
int j = 30;
int &r3 = j;
const int &r4 = const_cast<const int &>(r3); // 总结:const_cast用来给基础数据类型,指针或者引用“加上”或者“去除”const
} typedef void(*func1)(int, int);
typedef int(*func2)(int, char*); void Test4()
{
// 基础数据类型 - 无法转换
// int a = 10;
// char c = reinterpret_cast<char>(a); // 指针
Building *pbuilding = nullptr;
Animal *ani = reinterpret_cast<Animal *>(pbuilding); // 引用
Building building;
Building &bref = building;
Animal &aniref = reinterpret_cast<Animal &>(bref); // 函数指针
func1 f1;
func2 f2 = reinterpret_cast<func2>(f1); // 总结:reinterpret_cast用于任意两个无关类型的指针或者引用的转换!
// 应该尽量避免在代码中使用类型转换!!!
}

C++ STL——类型转换的更多相关文章

  1. c++ operator操作符的两种用法:重载和隐式类型转换,string转其他基本数据类型的简洁实现string_cast

    C++中的operator主要有两个作用,一是操作符的重载,一是自定义对象类型的隐式转换.对于操作符的重载,许多人都不陌生,但是估计不少人都不太熟悉operator的第二种用法,即自定义对象类型的隐式 ...

  2. STL的string和wstring

    STL有字符串处理类——stirng和wstring,但是用的时候会觉得不是很方便,因为它不能像TCHAR一样根据定义的宏在char类型字符串和wchar_t进行转换,总不能因为程序要Unicode就 ...

  3. STL学习小结

    STL就是Standard Template Library,标准模板库.这可能是一个历史上最令人兴奋的工具的最无聊的术语.从根本上说,STL是一些"容器"的集合,这些" ...

  4. HDU 4287 Intelligent IME(string,map,stl,make_pair)

    题目 转载来的,有些stl和string的函数蛮好的: //numx[i]=string(sx); //把char[]类型转换成string类型 // mat.insert(make_pair(num ...

  5. make_pair() (STL)

    转载来的 Pairs C++标准程序库中凡是“必须返回两个值”的函数, 也都会利用pair对象 class pair可以将两个值视为一个单元.容器类别map和multimap就是使用pairs来管理其 ...

  6. STL笔记(6)标准库:标准库中的排序算法

    STL笔记(6)标准库:标准库中的排序算法 标准库:标准库中的排序算法The Standard Librarian: Sorting in the Standard Library Matthew A ...

  7. STL map 用法

    首先make_pair Pairs C++标准程序库中凡是"必须返回两个值"的函数, 也都会利用pair对象  class pair可以将两个值视为一个单元.容器类别map和mul ...

  8. STL map详细用法和make_pair函数

    今天练习华为上机测试题,遇到了map的用法,看来博客http://blog.csdn.net/sprintfwater/article/details/8765034:感觉很详细,博主的其他内容也值得 ...

  9. 关于Windows API、CRT和STL二三事

    1.本文编写目的    本文是为了帮助一些人弄清一些关于Windows API, C运行时程序库(CRT), 和标准C++库(STL)的基本概念.有很多人甚至是有经验的程序员在这些概念上是含糊不清的甚 ...

随机推荐

  1. Supervisor进程管理配置使用

    Supervisor进程管理 在后台应用中,有时候程序进程会异常中止退出,如果没有一个守护进程去守护这个应用进程我们就需要及时发现并重启进程.如果每一个应用进程都写一个自己的守护进程难免会比较麻烦,而 ...

  2. html图片自定义裁剪大小

    该插件后端使用ASP.NET MVC实现图片存储 该插件适用于需要固定显示缩略图片的文章列表! 演示地址:http://hhcf.top:8099/Cropper/Index 源码下载:https:/ ...

  3. hibernate入门配置及第一个hibernate程序

    学习了hibernate后就想先给大家分享一下它的配置方法: jar包导入 一.数据库表的创建   二.开启hibernate配置 编译器:eclipse 数据库:mysql 1.创建第一个xml文件 ...

  4. 使用Barrier分三步将大象放入冰箱

    class Program { //构造大象和冰箱 private static ElephantsAndFridges elephantsAndFridges = new ElephantsAndF ...

  5. a 标签的download 属性在谷歌浏览器下无法下载图片,如何处理?

    a 标签的download属性在下载图片文件的时候是如何的方便,可是可是谷歌浏览器不支持下载,而是下载打开新窗口预览图片.这个兼容性问题如何解决呢? 了解了一番,HTMLCanvasElement.t ...

  6. 低级键盘钩子,在WIN7以上版本的问题

    最近在项目用到低级键盘钩子.发现一个很奇怪的事情,在开发环境和测试环境下都正常运行的键盘钩子, 到了现场环境,总是偶发性出现 键盘钩子不能用了,而且退出时产生1404 错误. 后经过阅读MSDN 的R ...

  7. 从后台数据库查询的List数据怎么在前台combobox显示

    后台直接从数据库,通过jdbcTemplate查询数据,得到List数据集,里面是Map List<Map<String, Object>> list =  jdbcTempl ...

  8. ftp定时下载指定目录或文件脚本

    #! /bin/bash rpm -qa lftp &>/dev/null || yum install -y lftp lftp 160.106.0.34 << EOF c ...

  9. 题解 【NOIP2003】神经网络

    [NOIP2003]神经网络 Description 问题背景: 人工神经网络( Artificial Neural Network )是一种新兴的具有自我学习能力的计算系统,在模式识别.函数逼近及贷 ...

  10. 【转】css样式的书写顺序及原理——很重要!

    记得刚开始学习前端的时候,每次写css样式都是用到什么就在样式表后添加什么,完全没有考虑到样式属性的书写顺序对网页加载代码的影响.后来逐渐才知道正确的样式顺序不仅易于查看,并且也属于css样式优化的一 ...