591 字
2 分钟
【CPP】类型转换与异常
为什么 C++ 需要新的转换方式
C 风格 (Type)expr 与 Type(expr) 可在一次转换中完成多种语义(截断、指针转换、去掉 const 等),难以在代码中一眼看出意图,也不易在编译期拦截错误。
C++ 提供四种命名的转换,语义清晰、可检索。
四种 cast
| 转换 | 用途 | 安全性 |
|---|---|---|
static_cast | 相关类型之间的编译期转换 | 由程序员保证 |
dynamic_cast | 多态类型的运行时下行转换 | 有 RTTI 检查 |
const_cast | 增加或去掉 const/volatile | 仅改 cv 限定,不改类型布局 |
reinterpret_cast | 比特级重新解释 | 危险,极少使用 |
static_cast
double d = 3.14;int i = static_cast<int>(d);
Derived* pd = static_cast<Derived*>(pBase); // 下行:无运行时检查,不安全- 数值转换、显式调用单参数构造函数、无虚函数时的上行/下行指针转换。
- 不能去掉
const(用const_cast)。
dynamic_cast
要求基类至少有一个 虚函数(多态类型)。
Base* pb = /* 指向 Derived */;Derived* pd = dynamic_cast<Derived*>(pb);if (pd) { /* 确实是 Derived */ }
try { Derived& dr = dynamic_cast<Derived&>(*pb);} catch (const std::bad_cast&) { /* 引用失败抛异常 */ }- 指针失败 →
nullptr;引用失败 →std::bad_cast。 - 有运行时开销(RTTI)。
const_cast
const int ci = 10;int* p = const_cast<int*>(&ci);// *p = 20; // 若 ci 在只读段,未定义行为仅用于去掉/添加 const、volatile;不能改变除 cv 外的类型。
reinterpret_cast
intptr_t addr = reinterpret_cast<intptr_t>(ptr);用于指针与整数、无关类型指针之间;可移植性差,除非底层/互操作必需,否则避免。
父类转子类(原笔记要点)
- 上行(派生 → 基类):隐式、安全。
- 下行(基类 → 派生):应用
dynamic_cast或确保对象真实类型,避免static_cast盲目下行。
异常 (exception)
异常:程序运行时出现的错误或非预期路径,通过 throw 抛出,沿调用栈展开,由匹配的 catch 处理。
double divide(double a, double b) { if (b == 0) throw std::invalid_argument("division by zero"); return a / b;}
try { double r = divide(1, 0);} catch (const std::invalid_argument& e) { std::cerr << e.what() << '\n';} catch (...) { std::cerr << "unknown error\n";}机制:
try:可能抛异常的代码。throw:抛出对象(通常是std::exception派生类)。catch:按类型匹配;派生类 catch 须写在基类之前。- 未捕获异常 → 调用
std::terminate。
规范:
- 按const 引用捕获,避免切片:
catch (const std::exception& e)。 - 析构函数默认
noexcept;析构中抛异常危险。 - 资源管理配合 RAII,异常安全等级(基本/强/不抛)与智能指针、移动语义相关。
不宜用异常的场景:极热路径、嵌入式无异常支持的编译选项(-fno-exceptions)。
RTTI
Runtime Type Identification:typeid、dynamic_cast 依赖运行时类型信息。可 -fno-rtti 关闭以减小体积(则 dynamic_cast 受限)。
分享
如果这篇文章对你有帮助,欢迎分享给更多人!
【CPP】类型转换与异常
https://lysj.work/posts/studynotes/cpp/cpp类型转换与异常/ 部分信息可能已经过时
相关文章 智能推荐
1
【C】输入输出与类型转换
StudyNote 介绍 printf、scanf 等标准 I/O 函数,以及赋值、算术隐式转换与强制类型转换的用法与注意点。
2
【CPP】内存与指针
StudyNotes 进程地址空间、new/delete、malloc/free 及智能指针 RAII 要点。
3
【CPP】基础与命名空间
StudyNotes C/C++ 差异、命名空间、函数重载及面向对象三大特征速查。
4
【CPP】继承与多态
StudyNotes 继承方式、虚函数、纯虚函数、菱形继承与 dynamic_cast。
5
【CPP】引用与值类别
StudyNotes 左值右值、左值引用与右值引用、const 引用及移动语义入门。
