[英]Unexpected output with left shift operator C++
這是給我意想不到的答案的代碼
#include<bits/stdc++.h>
using namespace std;
int main()
{
cout<<(1<<50);
}
我得到的答案是0。但是如果我將行更改為
cout<<pow(2, 50);
我得到正確的答案。
有人可以向我解釋原因。
假設您的編譯器將常數1
視為32位整數,則將其向左移動了很遠,這樣在您擁有的32位中只有零。 50大於32。
從C ++標准(5.8移位運算符)開始
1移位運算符<<和>>從左到右分組。
shift-expression:
additive-expression
shift-expression << additive-expression
shift-expression >> additive-expression
操作數應為整數或無作用域枚舉類型,並執行整數提升。 結果的類型是提升后的左操作數的類型。 如果右操作數為負或大於或等於提升后的左操作數的位長度, 則該行為是不確定的 。
請注意,如果右操作數不大於或等於左操作數的位長度,但由於整數文字1
的類型為signed int
類型,因此可以觸摸符號位,因此行為也將不確定。
對於此函數調用pow(2, 50)
,則使用某種算法來計算功率。
試試這個( 運行它 ):
#include <iostream>
int main()
{
std::int64_t i { 1 }; // wide enough to allow 50 bits shift
std::cout << std::hex << ( i << 50 ); // should display 4000000000000
return 0;
}
您將“ 1”移出了32位字段,因此結果為零。 Pow使用浮點表示形式,可以處理2 ^ 50。
編輯
如果不進行任何類似“ 1LL”或“ 1ULL”的修改(生成長的64位數字),則在x64或x86體系結構中,整數通常被處理為32位。 您可以使用
cout << (1ULL << 50);
要么
cout << ((long long)1 << 50);
哪個應該。
這就是你在做什么。 您正在將一部分內存(即32位內存)的位置移位50位。根據您的情況,這是怎么回事? 該位移至其他位置,但不再位於整數的內存部分內。 pow(2, 50)
執行double
強制轉換,因此您不再需要移位位。
另外,切勿使用#include<bits/stdc++.h>
。 它不是標准的 ,而且很慢。 您應該只在預編譯的頭文件中使用它,但在那種情況下,我也避免這樣做。
cout<<(1<<50);
您的代碼將1
視為int
,因此溢出。 相反,請嘗試:
cout << (1ULL << 50);
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.