[英]About reinterpret_cast and pointer
我正在学习C和C ++。 在这个计划中:
#include <iostream>
int main() {
const int g = 10;
int * k = reinterpret_cast <int *> (20000); //ok
std::cout << "k : " << k << std::endl;
std::cout << "* k : " << * k << std::endl;
* k = g;
std::cout << "* k : " << *k << std::endl;
return 0;
}
./converForTyEn
k:0x4e20分段错误(核心转储)
我希望20000然后是10.但似乎错误是“意味着你试图访问你无法访问的内存。” (Erci Finn)。 谢谢你的帮助。
该标准的工作草案(N4713)陈述了关于使用的标准
8.5.1.10重新解释强制转换
...
5. 可以将整数类型或枚举类型的值显式转换为指针 。 转换为足够大小的整数(如果实现上存在任何此类)并返回相同指针类型的指针将具有其原始值; 指针和整数之间的映射在其他方面是实现定义的。 [注意: 除6.6.4.4.3中描述的情况外,这种转换的结果不是安全派生的指针值 。 - 尾注]
和:
6.6.4.4.3安全派生指针[basic.stc.dynamic.safety]
...
2. 指针值是指向动态对象的安全派生指针,只有它具有对象指针类型且它是以下之一 :
(2.1) - 调用:: operator new(std :: size_t)或:: operator new(std :: size_t,std :: align_val_t)的C ++标准库实现返回的值;
(2.2) - 通过安全导出的指针值获取由间接导致的左值指定的对象(或其子对象之一)的地址的结果;
(2.3) - 使用安全派生的指针值定义良好的指针算法的结果;
(2.4) - 安全派生指针值的明确定义的指针转换结果;
(2.5) - 安全派生指针值的reinterpret_cast的结果;
(2.6) - 对安全派生的指针值的整数表示的reinterpret_cast的结果;
(2.7) - 从可跟踪指针对象复制其值的对象的值,其中在复制时源对象包含安全派生的指针值的副本。
由于您在整数文字( 20000
)上使用reinterpret_cast
,因此转换的结果不是安全派生的指针值。 尝试取消引用此类指针值会导致未定义的行为。
指针必须指向要使用的有效内存。 在您的情况下,您将其设置为任意内存位置,20000。
有效指针使用的一个例子是
int x = 42;
int *px = &x;
这将x
的地址放入px
。
std::cout << px;
会输出地址。
std::cout << *px;
会输出x
的值。
您的代码调用未定义的行为(UB),可能的输出将是:
k : 0x4e20
Segmentation fault
其中第一行是k
的地址。 然后,在这行代码中:
std::cout << "* k : " << * k << std::endl;
您正在尝试访问此地址,该地址不在您的程序段中,从而导致分段错误。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.