c++ - C++ 中的类型转换

标签 c++

我正在阅读一本 C++ 书籍,但遇到静态转换方面的问题。这是一个函数:

void fun(int*pi)
{
    void *pv = pi
    int *pi2 = static_cast<int*>(pv);  //explicit conversion back to int*
    double *pd3 = static_cast<double*>(pv);  //unsafe 

}

最后声明:

double*pd3 = static_cast<double*>(pv); 

被认为是不安全的。我不明白为什么它被认为是不安全的。

最佳答案

Actor 重新解释指向int的位,加上可能的一些后续内存(如果有的话!),作为 double值(value)。

A double是 (1) 通常大于 int , (2) 有一些内部结构。

点 (1) 意味着任何对解引用结果指针的使用都可能访问无法访问的内存,超出 int 范围。 .

点 (2) 表示任意位模式,可能是 无效 作为 double位模式,并且在使用时可能导致硬件异常 a.k.a. 一个“陷阱”。从 C++ 的角度来看,这是未定义的行为。从实际编程的角度来看,这通常是“崩溃”。

相比之下,访问 double 的位作为int通常在实践中是安全的,即使它是正式的 UB,因为 (1) int通常小于或等于 double ,和 (2) int通常没有任何无效的位模式。但是,根据编译器选项,编译器可能不喜欢直接这样做。


正如 Loki Astari 在评论中指出的那样,我在上面忘记提及对齐。这就是不安全的原因 (3)。例如,对于一些给定的实现 int可以允许地址是 4 的倍数,而 double可能需要驻留在 8 的倍数的地址。然后取消引用的指针可能会访问 double。在一个不是 8 的倍数的地址处,导致陷阱(更正式地说,UB,任何事情都可能发生)。

关于c++ - C++ 中的类型转换,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/20732406/

相关文章:

c++ - #ifndef 仅适用于 "declaration"部分?

c++ - Xcode 6 : Create pure C++ OpenGL application bundle (. 应用程序)不使用 "Cocoa Application"模板

c++ - 如何在 C 中访问 SOAP header

c++ - Q_OBJECT 导致 'undefined reference to v_table' 问题

C++ 使用 'tweaked' 比较仿函数排序

c++ - For Loop 函数参数错误

c++ - "%include"和 "#include"之间的区别

c++ - 如何将模板化类作为默认模板类型传递给自己的类?

c++ - 为什么绑定(bind)到引用类型时 "const auto [x, y]"的行为不符合预期?

c++ - 如何使用 `execl()` 在 C/C++ 中运行系统命令,将函数参数仅作为命令行而不是可执行文件传递?