强制类型转换

强制类型转换

一、C风格的强制类型转换
在C语言中,强制类型转换是通过“(目标类型)变量名”或者“目标类型(变量名)所实现的”,例如(int)3.14或者int(3.14),前者的方式常称之为C风格的类型转换,后者则被称之为函数风格的强制类型转换

二、static_cast

static_cast<目标类型>(expression)

static即为静态类型转换,在编译时进行类型检查以及类型转换,但没有运行时类型检查来保障安全性,其作用主要有4个

1.相关类型间的转换,double->int,int->double,float->int 等等

double pi = 3.14;
int k = static_cast<int>(pi);

2.子类对象向父类对象的转换,子类对象向父类对象相当于对子类对象进行了一个“切片”,只会保留父类中存在的信息

Base b = static_cast<Base>(derived_ins);

注意:把子类的指针或引用转换成基类表示是安全的,进行的是上行转换是安全的,把父类转换成字类时,进行下行转换,由于没有动态类型检查,所以是不安全的
3.void * 与其他类型指针的转换, operator new 就是使用static_cast将void *转换成指向具体对象的指针

void *memory = operator new(sizeof(Buz());
buz = static_cast<Buz *>(memory);

4.左值和右值之间的转换,move()方法将一个左值转换成右值,其内部就是使用static_cast实现的

三丶dynamic_cast

dynamic_cast<目标类型>(expression)

dynamic_cast主要用于父类和字类之间的类型转换,能够将父类指针或者引用安全的转换成子类的指针或者引用,这个过程发生在运行时,并且dynamic_cast正确工作的前提时父类中至少存在一个虚函数也就是说,dynamic_cast主要用在多态类类型,有时候我们需要将基类指针特例化,就可以使用类模板进行类型转换

当转换目标是指针时,也就是子类指针,如果转换失败,则返回空指针,当我们转换目标是引用时,也就是子类引用,若转换失败,则会抛出bad_cas异常,因为没有空引用

四、const_cast

const_cast<目标类型>(expression)

const_cast的主要作用就是添加或去除指针或者引用的const属性,但不可以是值类型,该类型转换绝大部分出现在函数重载中,其余场合使用const_cast去除const属性是一个很危险的行为

int a = 1;
const int* ptr = &a;

int* ktr = const_cast<int *>(ptr);
*ktr = 2;
cout<<*ktr<<endl;

这段代码能够正常编译和运行,但是强烈建议不要这么做,很容易引发系统漏洞

用途:函数重载
比如有一个这样的函数,接收两个string,返回长度较长的那个

string& longer_string(string& a, string& b) {
    return a.size() > b.size() ? a : b;
}

这个函数有个局限性,不能接受const实参,不能接收右值,改良后如下

const string& longer_string(const string& a, const string& b) {
    return a.size() > b.size() ? a : b;
}

这样就没问题了,const和非const字符串都能使用
但是上面改良的版本也有问题,因为不管实参是否带有const属性的,我们的longer_string都将其隐式的转换成了常量引用了

string& longer_string(string& a, string& b) {
    auto& r = longer_string(const_cast<const string&>(a), const_cast<const string&>(b));
    return const_cast<string&>(r);
}

这样一来,我们就不再需要在longer_string的非常量引用的重载函数中重复书写逻辑,而只是进行一些类型转换,最后一个版本我们首先利用const_cast为形参添加const属性,得到的结果再去除const属性,行为安全。因此,对于一个非常量的指针或者引用来说,我们可以先将其转换成const指针或者引用,然后做一些事情,事情一做完,再把它们的const属性摘掉,大家就当无事发生过。
const_cast只对底层const有用,对于顶层const没用

五丶reinterpret_cast

reinterpret<目标类型>(expression)

reinterpret_cast主要用于处理无关类型间的转换,也就是说两个转换类型之间没有任何关系,怎么转都行

常见用途:将一种类型指针转换成另一种类型的指针,按照转换后的内存重新解释内存中的内容

    int i = 68;
    int* ptr = &i;

    char* ktr = reinterpret_cast<char*>(ptr);
    cout << *ktr << endl;

这里我们将int指针转换成了char类型的指针,也就是说原本ptr指针读取4字节的内容,而ktr能只会读取变量i的第一个字节

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值