写这个随笔说一下C++的static_cast和dynamic_cast用在子类与父类的指针转换时的一些事宜。首先,【static_cast,dynamic_cast】【父类指针,子类指针】,两两一组,共有4种组合:用 static_cast 父类转子类、用 static_cast 子类转父类、使用 dynamic_cast 父类转子类、用 dynamic_cast 子类转父类。搞清楚了这4种情况,这篇文章的任务也就达成了。

先说结论,后面给出一个作者觉得通俗易懂的理解:

1. static_cast : 父类转子类:可以转,不报错,不安全;

2.static_casrt : 子类转父类:可以转,不报错,安全;

3.dynamic_cast : 父类转子类 :

  a)若父类中没有虚函数,不能转,编译报错;

  b)若父类至少有一个虚函数则可以转,不报错;但:

    b.1)若父类指针指向的确实是一个子类对象,则dynamic_cast返回该子类对象的地址;

    b.2)若父类指针指向的是父类对象,则dynamic_cast返回空指针nullptr;

4.dynamic_cast:子类转父类:可以转,不报错,安全。

总体来看,子类指针父类指针无论怎样都是安全、允许的(上面的2、4),所以static_cast和dynamic_cast都可以安全使用。

再说上面的1、3。 其实,static_cast相当于我们程序员对编译器的一种承诺:我们清楚地知道这样转存在的任何风险,并且我们能够接受这样的风险。所以,当我们用static_cast将父类指针转换成子类指针时,编译器不报错。而dynamic_cast是在运行时执行类型转换,用于将基类的指针安全地转换成派生类的指针,也就是说,dynamic_cast会进行动态类型检查。dynamic_cast相当于给程序员提供了一种安全的机制,让程序员能够安全地使用父类指针的动态类型。

下面举一个使用dynamic_cast(以上3中的b)的例子。首先给出父类和子类的定义:

class B
{
public:
virtual ~B() {};
}; class D : public B
{ };

若有以上类的定义:

代码1:

B* pb = new B;
if( D* p3 = dynamic_cast<D*>(pb) )
{
cout << "成功了" << endl;
  //若程序到此处,则程序员知道,pb指向的实际上是子类对象,可以使用p3
}
else {
cout << "失败了" << endl;
  //若程序到此处,则程序员知道,pb指向的实际上是父类对象,使用pb
}

输出:失败了。因为动态运行时,pb指向的是父类,并不是子类。

代码2:

B* pb = new D;
if( D* p3 = dynamic_cast<D*>(pb) )
{
cout << "成功了" << endl;
  //若程序到此处,则程序员知道,pb指向的实际上是子类对象,可以使用p3
}
else {
cout << "失败了" << endl;
  //若程序到此处,则程序员知道,pb指向的实际上是父类对象,使用pb
}

输出:成功了。

static_cast与dynamic_cast到底是什么?的更多相关文章

  1. static_cast 和 dynamic_cast 的区别

    static_cast一般用来将枚举类型转换成整型,或者整型转换成浮点型.也可以用来将指向父类的指针转换成指向子类的指针.做这些转换前,你必须确定要转换的数据确实是目标类型的数据,因为static_c ...

  2. c++中的强制转换static_cast、dynamic_cast、reinterpret_cast的不同用法儿

    c++中的强制转换static_cast.dynamic_cast.reinterpret_cast的不同用法儿   虽然const_cast是用来去除变量的const限定,但是static_cast ...

  3. C++强制类型转换:static_cast、dynamic_cast、const_cast、reinterpret_cast

    1. c强制转换与c++强制转换 c语言强制类型转换主要用于基础的数据类型间的转换,语法为: (type-id)expression//转换格式1 type-id(expression)//转换格式2 ...

  4. C++中static_cast和dynamic_cast强制类型转换

    在C++标准中,提供了关于类型层次转换中的两个关键字static_cast和dynamic_cast. 一.static_cast关键字(编译时类型检查) 用法:static_cast < ty ...

  5. C++的类型转换:static_cast、dynamic_cast、reinterpret_cast和const_cast

    在C++中,存在类型转换,通常意味着存在缺陷(并非绝对).所以,对于类型转换,有如下几个原则:(1)尽量避免类型转换,包括隐式的类型转换(2)如果需要类型转换,尽量使用显式的类型转换,在编译期间转换( ...

  6. 四种强制类型转换的总结(const_cast、static_cast、dynamic_cast、reinterpreter_cast)

    四种强制类型转换的总结(const_cast.static_cast.dynamic_cast.reinterpreter_cast) 转载 2011年10月03日 23:59:05 标签: stru ...

  7. static_cast、dynamic_cast、reinterpret_cast、和const_cast

    关于强制类型转换的问题,很多书都讨论过,写的最详细的是C++ 之父的<C++ 的设计和演化>.最好的解决方法就是不要使用C风格的强制类型转换,而是使用标准C++的类型转换符:static_ ...

  8. static_cast 和 dynamic_cast

    1.static_cast static_cast < type-id > ( expression ) 该运算符把expression转换为type-id类型,但没有运行时类型检查来保证 ...

  9. C++ ------ static_cast,dynamic_cast,reinterpret_cast,const_cast

    C++类型转换分为:隐式类型转换和显式类型转换 第1部分. 隐式类型转换 又称为“标准转换”,包括以下几种情况:1) 算术转换(Arithmetic conversion) : 在混合类型的算术表达式 ...

  10. static_cast、dynamic_cast、const_cast和reinterpret_cast总结(转)

    前言 这篇文章总结的是C++中的类型转换,这些小的知识点,有的时候,自己不是很注意,但是在实际开发中确实经常使用的.俗话说的好,不懂自己写的代码的程序员,不是好的程序员:如果一个程序员对于自己写的代码 ...

随机推荐

  1. WPF之事件

    目录 WPF的树形结构 事件 路由事件 使用WPF内置路由事件 自定义路由事件 ButtonBase类的Click路由事件 创建一个路由事件 RoutedEventArgs的Source与Origin ...

  2. 线上机器 swap 过高导致告警

    哈喽大家好,我是咸鱼. 今天收到了一个告警,说有台服务器上的 swap 过高,已经用了 50% 以上了. 登录机器查看一下内存以及 swap 的使用情况. [root@localhost ~]# fr ...

  3. RSA算法揭秘:加密世界的守护者

    RSA算法起源: RSA算法是由Ron Rivest.Adi Shamir和Leonard Adleman在1977年共同提出的.它是一种非对称加密算法,基于两个大素数的乘积难以分解的数论问题.RSA ...

  4. Newtonsoft.Json/Json.NET忽略序列化时的意外错误

    在.NET中Newtonsoft.Json(Json.NET)是我们常用来进行Json序列化与反序列化的库. 而在使用中常会遇到反序列化Json时,遇到不规则的Json数据解构而抛出异常. Newto ...

  5. Android 接收微信、QQ其他应用打开,第三方分享

    这里给大家分享我在网上总结出来的一些知识,希望对大家有所帮助 在AndroidManifest.xml注册ACTION事件 <activity android:name="com.te ...

  6. 一文讲透Java核心技术之高可扩展利器SPI

    大家好,我是冰河~~ SPI的概念 JAVA SPI = 基于接口的编程+策略模式+配置文件 的动态加载机制 SPI的使用场景 Java是一种面向对象语言,虽然Java8开始支持函数式编程和Strea ...

  7. 一些 IL 语言解释

    跳转指令集合 Public field Static     Beq     如果两个值相等,则将控制转移到目标指令. Public field Static     Beq_S     如果两个值相 ...

  8. KingbaseES 支持自定义异常

    KingbaseES PLSQL 从 V8R6C4 版本开始,支持用户自定义异常.具体例子如下: create or replace procedure p_test() as error_numbe ...

  9. 表的唯一约束的作用 KingbaseES VS Oracle

    背景 演示唯一约束怎样创建.删除.禁用和使用唯一性约束,已经多种数据库的差异. 什么是唯一约束 唯一性约束指表中一个字段或者多个字段联合起来可以唯一标识一条记录的约束, 字段中,可以包括空值. 唯一性 ...

  10. #树状数组,欧拉函数#CF594D REQ

    题目 给定 \(n\) 个数,求 \(\varphi(\prod_{i=l}^r{a_i})\) 分析 考虑单个欧拉函数的求法,只需要求出这个数的质因数计算即可. 那么考虑离线,枚举右端点,记录每个质 ...