文学起点网
当前位置: 首页 文学百科

c强制类型转换规则(c语言强制转化的正确使用)

时间:2023-05-23 作者: 小编 阅读量: 1 栏目名: 文学百科

dynamic_cast是四个强制类型转换操作符中最特殊的一个,它支持运行时识别指针或引用。它对编译器有要求,需要编译器启动“运行时类型信息”这一选项。dynamic_cast与继承层次的指针对于“向下转型”有两种情况。当然,虚函数表的建立对效率是有一定影响的,构建虚函数表、由表查询函数都需要时间和空间上的消耗。所以,除了必须声明virtual,不要轻易使用virtual函数。对于虚函数的进一步了解,可以查看《EffectiveC++》

dynamic_cast是四个强制类型转换操作符中最特殊的一个,它支持运行时识别指针或引用。

>>>>>>>>>>>编译器的RTTI设置>>>>>>>>>>>

dynamic_cast提供RTTI(Run-Time Type Information),也就是运行时类型识别。它对编译器有要求,需要编译器启动“运行时类型信息”这一选项。当编译器不开启RTTI时,运行含有dynamic_cast操作符的程序时会出现一个警告:

warning C4541: “dynamic_cast”用在了带 /GR- 的多态类型“ANIMAL”上;可能导致不可预知的行为

VS2010在默认下是开启RTTI的,也可以自己手动去开启或者关闭,操作如下:

视图->解决方案资源管理器
在打开的解决方案管理器中,对着项目名称右击,选择属性
配置属性-〉C/C++

>>>>>>>>>>>>>步入正题>>>>>>>>>>>>>

  • dynamic_cast主要用于“安全地向下转型”

dynamic_cast用于类继承层次间的指针或引用转换。主要还是用于执行“安全的向下转型(safe downcasting)”,也即是基类对象的指针或引用转换为同一继承层次的其他指针或引用。至于“先上转型”(即派生类指针或引用类型转换为其基类类型),本身就是安全的,尽管可以使用dynamic_cast进行转换,但这是没必要的, 普通的转换已经可以达到目的,毕竟使用dynamic_cast是需要开销的。

class Base{public:Base(){};virtual void Show(){cout<<"This is Base calss";}};class Derived:public Base{public:Derived(){};void Show(){cout<<"This is Derived class";}};int main(){Base *base ;Derived *der = new Derived;//base = dynamic_cast<Base*>(der); //正确,但不必要。base = der; //先上转换总是安全的base->Show();system("pause");}学习交流群:894479708欢迎所有初学和进阶者一起讨论学习!

dynamic_cast与继承层次的指针

对于“向下转型”有两种情况。一种是基类指针所指对象是派生类类型的,这种转换是安全的;另一种是基类指针所指对象为基类类型,在这种情况下dynamic_cast在运行时做检查,转换失败,返回结果为0;

#include "stdafx.h"#include<iostream>using namespace std;class Base{public:Base(){};virtual void Show(){cout<<"This is Base calss";}};class Derived:public Base{public:Derived(){};void Show(){cout<<"This is Derived class";}};int main(){//这是第一种情况Base* base = new Derived;if(Derived *der= dynamic_cast<Derived*>(base)){cout<<"第一种情况转换成功"<<endl;der->Show();cout<<endl;}//这是第二种情况Base * base1 = new Base;if(Derived *der1 = dynamic_cast<Derived*>(base1)){cout<<"第二种情况转换成功"<<endl;der1->Show();}else{cout<<"第二种情况转换失败"<<endl;}学习交流群:894479708欢迎所有初学和进阶者一起讨论学习!delete(base);delete(base1);system("pause");}

运行结果:

  • dynamic_cast和引用类型

在前面的例子中,使用了dynamic_cast将基类指针转换为派生类指针,也可以使用dynamic_cast将基类引用转换为派生类引用。

同样的,引用的向上转换总是安全的:

Derived c;Derived & der2= c;Base & base2= dynamic_cast<Base&>(der2);//向上转换,安全base2.Show();

所以,在引用上,dynamic_cast依旧是常用于“安全的向下转型”。与指针一样,引用的向下转型也可以分为两种情况,与指针不同的是,并不存在空引用,所以引用的dynamic_cast检测失败时会抛出一个bad_cast异常:

int main(){//第一种情况,转换成功Derived b ;Base &base1= b;Derived &der1 = dynamic_cast<Derived&>(base1);cout<<"第一种情况:";der1.Show();cout<<endl;//第二种情况Base a ;Base &base = a ;cout<<"第二种情况:";try{Derived & der = dynamic_cast<Derived&>(base);}catch(bad_cast)学习交流群:894479708欢迎所有初学和进阶者一起讨论学习!{cout<<"转化失败,抛出bad_cast异常"<<endl;}system("pause");}

运行结果:

  • 使用dynamic_cast转换的Base类至少带有一个虚函数

当一个类中拥有至少一个虚函数的时候,编译器会为该类构建出一个虚函数表(virtual method table),虚函数表记录了虚函数的地址。如果该类派生了其他子类,且子类定义并实现了基类的虚函数,那么虚函数表会将该函数指向新的地址。虚表是C++多态实现的一个重要手段,也是dynamic_cast操作符转换能够进行的前提条件。当类没有虚函数表的时候(也即一个虚函数都没有定义),dynamic_cast无法使用RTTI,不能通过编译(个人猜想…有待验证)。

当然,虚函数表的建立对效率是有一定影响的,构建虚函数表、由表查询函数 都需要时间和空间上的消耗。所以,除了必须声明virtual(对于一个多态基类而言),不要轻易使用virtual函数。对于虚函数的进一步了解,可以查看《Effective C++》

    推荐阅读
  • 供电运维队长职责(奋进供电人杨晶晶)

    2013年入职南方电网深圳供电局以来,她从事新闻宣传工作已经9个年头。从小就有着“新闻梦”的杨晶晶,以笔为媒,做深圳电网与公众间的“桥梁”“窗口”。打开杨晶晶的电脑文件夹,她“码”下的每一篇稿件按“年度-季度”分类存档。自2018年来到深圳供电局新闻中心以来,她累计写稿超过了36万字。杨晶晶记得,2020年,新冠肺炎疫情突然袭来,她因居家办公无法到现场采访。

  • 中秋月圆夜难眠(中秋月圆之夜有荞麦)

    众所周知,荞麦是一种健康的食物。赤峰荞麦文化协会成立于2017年8月3日,是以发掘荞麦文化产业为宗旨,不断的创新研发荞麦文化及产品。近期还研发了荞麦壳床垫,一面使用羊毛毡垫,另一面使用荞麦壳填充。荞麦全身都是宝,一方水土养一方荞麦。将会有更多的荞麦品牌相继推出,将赤峰荞麦这张名片推向全国!

  • 早餐什么时候吃最好(吃早餐的最佳时间是几点)

    早餐最好在早上7点后吃。医学专家指出,人在睡眠时,绝大部分器官都得到了充分休息,而消化器官却仍在消化吸收晚餐存留在胃肠道中的食物,到早晨才渐渐进入休息状态。一旦吃早餐太早,势必会干扰胃肠的休息,使消化系统长期处于疲劳应战的状态,扰乱肠胃的蠕动节奏。另外,早餐与午餐以间隔4至5小时左右为好,也就是说早餐7至8点之间为好,如果早餐过早,那么数量应该相应增加或者将午餐相应提前。

  • 死亡笔记中硫克最后在笔记本上写夜神月的名字的真正原因终于揭晓(死亡笔记中硫克最后在笔记本上写夜神月的名字的真正原因终于揭晓)

    死亡笔记中硫克最后在笔记本上写夜神月的名字的真正原因终于揭晓?夜神月被捕,肯定会被判死刑,寿命本来就已经到尽头了,夜神月让硫克用笔记杀死其他人,硫克如果照办,就等于是帮助月延长了生命,硫克就会死。另外,死亡笔记有规则,当死亡笔记在人间的第一个拥有者死亡时,死神必须要在自己的那本笔记上写上此拥有者的名字,相当于一个契约,拿到笔记本成为拥有者契约开始,最后第一个拥有者死亡时,死神写上名字契约结束。

  • 玻璃钢与碳钢哪个更好(林森为大家讲述玻璃钢是玻璃)

    玻璃钢也称作SMC,即纤维强化塑料,一般指用玻璃纤维增强不饱和聚脂、环氧树脂与酚醛树脂基体。以玻璃纤维或其制品作增强材料的增强塑料,称为玻璃纤维增强塑料,或称玻璃钢。无机玻璃钢由于所使用的树脂品种不同,因此有聚酯玻璃钢、环氧玻璃钢、酚醛玻璃钢之称。基体相对于纤维来说,强度、模量都要低很多,但可以经受住大的应变,往往具有粘弹性和弹塑性,是韧性材料。

  • 主动脉硬化是怎么回事(主动脉硬化是怎么回事怎么治疗)

    动脉硬化是随着年龄增长而出现的血管疾病,其规律通常是在青少年时期发生,至中老年时期加重、发病。引起主动脉硬化的病因中最重要的是高血压、高脂血症、抽烟。因此说服患者耐心接受长期的防治措施至关重要。若血脂持续增高,应食用低胆固醇、低动物性脂肪食物,如:各种瘦肉,鸡、鸭、鱼肉,蛋白,豆制品等。参加一定的体力劳动和体育活动,对预防肥胖、锻炼循环系统的功能和调整血脂代谢均有禆益,是预防本病的一项积极措施。

  • 失业金领取条件及标准(失业金领取条件及标准是什么)

    我们一起去了解并探讨一下这个问题吧!失业金领取条件及标准失业保险金领取条件有:具备下列条件的失业人员,可以领取失业保险金。按照规定参加失业保险,所在单位和本人已按照规定履行缴费义务满1年的;非因本人意愿中断就业的;已依法定程序办理失业登记的;有求职要求,愿意接受职业培训、职业介绍的。

  • 如何做爽口萝卜(爽口萝卜制作步骤)

    如何做爽口萝卜材料:白萝卜600g,白醋40,盐10g,糖50g,小米椒5个。米醋和糖的比例可以按自己对酸甜的喜好来配比调整。撒上10g盐搅拌均匀,腌制大约半小时,使得白萝卜软化脱水去辛辣。加入小米椒、糖、白醋。萝卜倒进密封的保鲜盒或玻璃罐。放进冰箱冷藏保存,腌几个小时就可以吃了,隔天后的白萝卜更好吃。每次吃的时候取出一部分,然后放回冰箱,随着腌制时间延长,吃到最后越来越好吃。

  • 酸汤肥牛金针菇的做法(金汤肥牛)

    金汤肥牛酸辣爽口,非常开胃,将肥牛煮在酸爽辛辣的金汤里,用金针菇做配菜非常适合。

  • 出去游玩是清明节的习俗吗(清明节古人玩什么吃什么)

    清明,不仅是季春三月的一个节气,还是传统民俗文化中一个重要节日。清明是扫墓节,因为融合了寒食节。古代寒食节在冬至后一百零五天,恰与汉代以后出现的清明节气贴近。清明扫墓、缅怀先人遂成风俗沿袭至今。清明又是踏青节,因为合并了上巳节。魏晋以后,将上巳节定为三月初三。元朝宫中更是盛行,每逢清明,宫女们穿上“蹴秋千之服”,双双对蹴。秋千是女人和儿童玩的,成年男子则以蹴鞠为戏。佳节有佳肴,清明要吃桃花饭。