![](/img/trans.png)
[英]Why type unsigned makes std::variant<int64_t,uint64_t> ambiguous to construct?
[英]Why -INT_MIN is NOT 2147483648 for uint64_t type
我理解p
的結果。 有人可以解釋為什么up2 (uint64_t type) != 2147483648
但up (uint32_t type) == 2147483648
嗎?
有人提到將 -INT_MIN 分配給無符號整數 up2 會導致溢出,但是
-INT_MIN
已經是一個正數了,所以可以把它分配給uint64_t up2
嗎?
為什么將-INT_MIN
分配給uint32_t up
似乎-INT_MIN
? 它產生正確的結果為 2147483648。
#include <iostream> #include <climits> using namespace std; int main() { int n = INT_MIN; int p = -n; uint32_t up = -n; uint64_t up2 = -n; cout << "n: " << n << endl; cout << "p: " << p << " up: " << up << " up2: " << up2 << endl; return 0; }
結果:
n: -2147483648 p: -2147483648 //because -INT_MIN = INT_MIN for signed integer up: 2147483648 //because up is unsigned int from 0 to 4,294,967,295 (2^32 − 1) and can cover 2147483648 up2: 18446744071562067968 //Question here. WHY up2 != up (2147483648)???
int p = -n;
的行為在 2 的補碼系統上未定義(接受您的問題中有錯字; INT_MAX
在這樣的系統上總是奇數),因為您的int
類型溢出。 所以你的整個程序是未定義的。
這就是為什么您會在許多庫中看到INT_MIN
定義為-INT_MAX - 1
。
請注意,當您由於有符號整數溢出而調用未定義行為時,以下是您所觀察到的行為的最可能解釋:
如果int
在您的系統上是 32 位,並且您的系統使用一個補碼或二進制補碼來存儲有符號整數,那么符號位將擴展為 64 位無符號類型的高 32 位。
如果您以 base-16 打印出您的值可能會更有意義。
n = 0x80000000
p=0x80000000
up=0x80000000
up2=0xFFFFFFFF80000000
您看到的是-n
轉換為uint64
,其中溢出不是 40 億,而是 2**64:
18446744073709551616 - 2147483648 = 18446744071562067968
您的情況下的表達式-n
會導致未定義的行為,因為結果無法適應int
數據類型的范圍。 (無論您是否將此未定義的結果分配給“更寬”類型的變量都無關緊要,反轉本身是用int
。)
試圖解釋未定義的行為是沒有意義的。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.