在互联网上,我发现了以下问题:
int a = (int)pow(2, 32);
cout << a;
Run Code Online (Sandbox Code Playgroud)
它在屏幕上打印什么?
首先我想到了0,但是在我编写代码并执行它之后,我得到了-2147483648,但为什么呢?
我也注意到了(int)(pow(2, 32) - pow(2, 31))等于-2147483648.
谁能解释为什么(int)pow(2, 32)等于-2147483648?
假设int您的计算机上有32位(或更少),这是未定义的行为.
从标准,conv.fpint:
可以将浮点类型的prvalue转换为整数类型的prvalue.转换截断; 也就是说,丢弃小数部分.如果截断的值无法在目标类型中表示,则行为未定义.
最常见的int是32位,它可以表示区间[-2^31, 2^31-1]中的值[-2147483648, 2147483647].结果std::pow(2, 32)是double表示确切值的结果2^32.由于2^32超出了可以表示的范围,int转换尝试是未定义的行为.这意味着在最好的情况下,结果可以是任何东西.
第二个例子也是如此:pow(2, 32) - pow(2, 31)只是double表示2^31,(几乎没有)超出32位可以表示的范围int.
这样做的正确方法是转换为足够大的整数类型,例如int64_t:
std::cout << static_cast<int64_t>(std::pow(2, 32)) << "\n"; // prints 4294967296
Run Code Online (Sandbox Code Playgroud)