我正在阅读一本 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/