C\C++_类型转换运算符

1. 类型转换运算符种类

关键概念:存在继承关系之间的转换规则

  • 从派生类向基类的类型转换只对指针或引用类型有效。
  • 基类向派生类不存在隐式类型转换。
  • 和任何其他成员一样,派生类向基类的类型转换也可能会由于访问受限而变得不可行。

参考书籍:C++ Primer (第5版)—— 15.2.3 类型转换与继承
| 类型转换运算符 | 作用| 语法|
|–|–|–|
| dynamic_cast | 将派生类指针转换为基类指针,主要是为了确保可以安全的调用虚函数 | dynamic_cast(expression)|
| const_cast | 有时需要这样一个值,它在大多数时候是常量,有时又想要修改,这时可以将这个值声音为const,在需要修改的时候使用const_cast |const_cast(expression) |
| static_cast | 当type_name可被隐式转换为expression所属的类型或expression可被隐式转换为type_name所属的类型时,转换才合法,否则将出错 | static_cast(expression)
| reinterpret_cast | 类似C语言中的指针指针类型转换,例如 int n = 20; char p = (char)&n;这里的(char*)即是C语言的强制类型转换语法 |reinterpret_cast(expression)

注意:与通用转换机制相比,这四种转换提供了更安全,更明确的类型转换

2. 代码示例

2.1 dynamic_cast

#include <iostream>
using namespace std;

class CPerson
{
public:
    virtual void Show()
    {
        cout << "CPerson" << endl;
    }
};

class CStudent : public CPerson
{
public:
    virtual void Show()
    {
        cout << "CStudent" << endl;
    }
};

int main()
{
	//! 将CStudent对象地址赋值给CPerson*:成功,返回CPerson*;失败,返回0(即空指针)
    CPerson *pPer = nullptr;
    if (pPer = dynamic_cast<CPerson *>(new CStudent)) //< 转换成功再调用虚函数
    {
        pPer->Show();
    }

    return 0;
}

2.2 const_cast

    int n = 10;
    const int *p = &n;
  	// *p = 29;  错误,无法指针指向的值

    int *p2 = const_cast<int*>(p);
    *p2 = 29;   //< 正确,可以删除const

2.3 static_cast

class CPerson{};
class CStudent: public CPerson{};   //< 继承CPerson
class CPond{};  //< 和Cperson,CStudent无关

int main()
{
    CPerson per;
    CStudent stu;
    CPerson *pPer = static_cast<CPerson*>(&stu);         //< 合法
    CStudent* pStu = static_cast<CStudent*>(&per);      //< 合法
   // CPond *pPon = static_cast<CPond*>(&stu);         //< 非法,CPond与CStudent不相关

    return 0;
}

2.4 reinterpret_cast

在这里插入图片描述

  • 通常,这样的转换适用于依赖于实现的底层编程技术,是不可移植的。例如,不同系统在存储多字节整形时,可能以不同的顺序存储其中的字节。
  • 并不支持所有的类型转换,例如,可以将指针类型转换为足以存储指针表示的整形,但不能将指针转换为更小的整数或者浮点型;另一个限制是,不能将函数指针转换为数据指针,反之亦然。
    StuPer stuP = {10, 20};
    cout << *(short*)((char*)(&stuP)+2) << endl;    //< C语言的指针类型转换语法取short b值,输出为20
    cout <<  *(reinterpret_cast<short*>( (reinterpret_cast<char*>(&stuP)+2)));     //< c++ 指针类型转换语法,输出为20

3. 参考书籍

C++ Primer Plus(第6版)——15.5 类型转换运算符

4. 尽量少做转型动作

effective c++ 条款27 尽量少做转型动作

类型转换运算符作用语法
dynamic_cast主要用来执行“安全向下转换”,也就是用来决定某对象是否归属继承体系中的某个类型,它是唯一无法由旧式语法执行的动作,也是唯一可能耗费重大运行成本的转型动作
const_cast通常被用来将对象的常量性转出(cast away the constness),它也是唯一有此能力的c+±sytle转型操作符
static_cast用来强迫隐式转换(implicit conversion),例如将non-const对象转为const对象(就像条款3所为),或将int转为double等等。它也可以用来执行上述多种转换的反向转换,例如将void*指针转为typed指针,将pointer-to-base转为pointer-to-derived。但它无法将const转为non-const——这个只有const_cast才办得到
reinterpret_casty意图执行低级转型,实际动作(及结果)可能取决于编译器,这也就表示它不可移植。例如将一个pointer to int转型为一个int。这一类转型在低级代码意外很少见。本书只使用一次,那是在讨论如何针对原始内存(raw memory)写出一个调试用的分配器(debugging allocator)时,见条款50
  • c++ primer 第五版——4.11.3 显示转换如下图
    在这里插入图片描述
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值