2012-06-29 220 views
3

在我公司的stdint.h標題寫着:爲什麼INT64_MIN有不同的定義?爲什麼他們的行爲有所不同?

#define INT64_MIN -9223372036854775808LL 

但在我的項目的一些代碼,程序員寫道:

#undef INT64_MIN 
#define INT64_MIN (-9223372036854775807LL -1) 

然後,他使用這個定義中的代碼。
該項目編譯時沒有警告/錯誤。
當我試圖消除他的定義,並使用默認的,我得到:

error: integer constant is so large that it is unsigned 

兩種定義似乎是等價的。
爲什麼一個編譯正常,另一個失敗?

+3

是不是有點嚇人,從一個標準的頭文件中的#define導致錯誤? – fvu

+0

@fvu:沒關係,事實證明問題在於,abelenky的僱主用自己的破解版本取代了標準頭文件(請參閱下面的註釋)。 –

+0

@SteveJessop我在討論中看到了這個看起來像一個漂亮的兔子想法給我。 – fvu

回答

15

-9223372036854775808LL不是一個單一的文字。這是一個表達式,由應用於常量9223372036854775808LL的一元運算符-組成。

即常數爲(勉強)long long類型的範圍,這將導致警告外部。

表達(-9223372036854775807LL -1),在另一方面,包含是long long的範圍內的文字,並且是 同樣 用於INT64_MIN一個更有效的定義,因爲它是正確類型的(如史蒂夫傑索普在指出評論)。

+0

很好的解釋。這是否意味着stdint.h中的定義是錯誤的,因爲它使用LL範圍之外的值? – abelenky

+1

@abelenky:不一定。只要它爲編譯器提供了正確的行爲*,它就是用來和*一起使用的,沒關係。即使它產生了一個虛假的警告,這並不會使它不符合 - 但我仍然認爲這是一個錯誤。請注意,我係統上的''使用'-1'技巧。你的系統是什麼,你的''是從哪裏來的? –

+0

我在一個64位的Linux系統上。 stdint.h來自公司的源代碼庫。我傾向於認爲它有一些Unix背景,但不知道它的歷史細節。 – abelenky

相關問題