C++学习记录(五)——类型转换运算符

        今天学习了C++类型转换运算符以及支持和反对类型转换运算符的根据。一般来说应该避免使用类型转换。

目录

1. C++类型转换运算符

1.1 使用static_cast

1.2 使用dynamic_cast和运行阶段类型识别

1.3 使用reinterpret_cast

1.4 使用const_cast


1. C++类型转换运算符

C++提供了新的类型转换运算符,专门用于基于继承的情形。C++类型的运算符有4个——static_cast, dynamic_cast, reinterpret_cast, const_cast。

1.1 使用static_cast

static_cast<type>(expression);

作用:将expression转换为type类型,转换发生在编译时。

使用场景:

用于类层次结构中基类和派生类之间指针或引用的转换,其中——向上转换是安全的,向下转换是不安全的,但两者均可以通过编译,也就是说开发者要负责强转的运行时安全性。

注:派生类向基类转换称为向上转换,是一种无需使用任何显式类型转换运算符就能进行的转换,是安全的;而基类向派生类转换称为向下转换,如果不使用显示类型转换运算符,就无法进行这种转换,是不安全的。

将隐式类型转换为显式类型,以引起程序员或代码阅读者的注意。

一些栗子:

class Base{};
class Derived: public Base{};

int main()
{
    //通过编译,且安全
    Derived* myDerived = new Derived();
    Base* myBase = static_cast<Base*>(myDerived);

    //通过编译,但不安全
    Base* objBase = new Base();
    Derived* objDerived = static_cast<Derived*>(objBase);

    //将隐式类型转换为显式类型
    double pi = 3.1415;
    int num = static_cast<int>(pi);

    return 0;
}

1.2 使用dynamic_cast和运行阶段类型识别

destination_type* Dest = dynamic_cast<class_type*>(source);
if(Dest)//检查转换是否成功
{
    Dest->CallFuc();
}

作用:将expression转换为type类型,与静态类型转换相反,动态类型转换在运行阶段(即应用程序运行时)执行类型转换,可以检查dynamic_cast的操作结果,以判断类型转换是否成功。P280/265

使用场景:

转换类型必须是一个指针、引用或者void*,用于将基类的指针或引用安全地转换成派生类的指针或引用;
② dynamic_cast在运行期间强制转换,运行时进行类型转换检查;
③ 对指针进行转换,失败返回null,成功返回type类型的对象指针,对于引用的转换,失败抛出一个bad_cast ,成功返回type类型的引用;
④ dynamic_cast不能用于内置类型的转换;
⑤ 用于类的转换,基类中一定要有virtual定义的虚函数(保证多态性),不然会编译错误。

注:务必检查dynamic_cast的返回值,看它是否有效。如果返回值为null,则说明转换失败。

1.3 使用reinterpret_cast

reinterpret_cast<type>(expression);

作用:将一种对象类型转换为另一种,不管它们是否相关。且它只改变对指针的解释,并不改变指向的对象。

使用场景:

① reinterpret_cast 运算符可用于 char* 到 int* 或 One_class* 到 Unrelated_class* 之类的转换,这本身并不安全,但可以通过编译;
② reinterpret_cast 的本质作用是重新定义内存数据的解释方式,而不进行任何二进制转换。

注意:最好别用这个...不安全。

1.4 使用const_cast

const_cast<type>(expression);

作用:弥补了static_cast无法转换const/volitale的不足,将expression的const/volitale属性移除,仅限于底层const属性。

使用场景:

const_cast通常对指针和引用进行转换,而无法直接移除内置类型的const/volitale属性,换言之,这种语法直接提供了一个具有写权限的指针或引用,可以通过间接访问的方式,修改常量。

#include<iostream>
using namespace std;

int main() {
    cout<<"请输入一个数:"<<endl;
    int input;
    cin>>input;
    const int a = input;
    const int*pointer_const = &a;
    int*b = const_cast<int*>(pointer_const);
    *b = 20;
    cout << "b = " << *b << endl;
    cout << "a = " << a << endl;
    cout << "b = " << b << endl;
    cout << "&a = " << &a << endl;

    return 0;
}

结果如下:


参考:CSDN博主「大山喵」的原创文章,链接:https://blog.csdn.net/CV_Jason/article/details/82116750

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值