2013-03-10 7 views
4
#include <sys/types.h> 
//Line 2: typedef unsigned int uint; 
//Line 3: typedef unsigned int uint; 
int main() { 
    uint a; 
    return 0; 
} 

鑑於上述的C代碼,它的編譯成功,對於UINT在<sys/types.h>定義。儘管它不是標準化的,但是它增加了SysV兼容性,在代碼中進行了評論。C編譯器是否區分用戶代碼和庫代碼中定義的類型?

取消註釋上述代碼的第二行仍然會導致編譯成功。據我瞭解,不允許重新定義一種類型,通過取消註釋第二行和第三行來確認,這將導致編譯錯誤。

編譯器如何足夠聰明地知道uint是在標準庫還是用戶代碼中定義的? gcc和clang都給出了一致的行爲。

編輯: 在這種情況下,鏈接不是遊戲的一部分。該錯誤僅在編譯時纔會複製,即(-c選項)。

添加行號以減少混淆。

編輯:

取消對上述代碼的第二行仍導致成功的編譯。據我瞭解,不允許重新定義一種類型,通過取消註釋第二行和第三行來確認,這將導致編譯錯誤。

我不知道爲什麼我寫了這一點。顯然,取消註釋第2行和第3行不會導致gcc的編譯錯誤。 Clang給出的默認編譯選項的錯誤要嚴格得多,可以通過傳遞一些參數來進行調整。

Here介紹多的typedef是否允許或沒有,這真可謂是相當複雜的。無論如何只是儘量避免重複的typedef。

+0

我很困惑你的問題。鏈接器知道代碼在哪裏,以及它在哪個部分構建。編譯器只會看到您或其他人定義的類型。如果你可以更詳細地闡述你的問題,這聽起來就像是你正在描述一種幫助構建程序的語言,它的組件基於某些權限運行。我對阿達一無所知,但你的描述讓我想起了我聽說過的阿達的描述。同樣,如果您可以編輯原始文章並進行更多解釋,這將會有所幫助。 – octopusgrabbus 2013-03-10 21:08:57

+1

我的gcc不會因2'typedef unsigned int uint'而生氣。現在,如果第二個人試圖將其重新聲明給其他人,那麼我得到一個錯誤。你使用什麼版本? – cnicutar 2013-03-10 21:09:28

+0

該類型只是編譯器魔術.. – 2013-03-10 21:09:33

回答

2

重複聲明在C語言中是完全有效的,所以如果您按照描述取消註釋這兩行,您將看不到任何錯誤,與您所說的相反。

有兩個不同聲明的名稱將是一個錯誤。

重複一個定義也是一個錯誤,但typedef不是定義(儘管def),它是一個聲明。

1

標準庫也是用戶代碼,通常由其他用戶編寫。

取消註釋上述代碼的第二行仍然會導致成功編譯。正如我明白,不允許重新定義一種類型,通過取消註釋第二行和第三行來確認,這將導致一個編譯錯誤。

在我的gcc沒有。 (版本4.5.3)

編譯器如何足夠聰明地知道uint是在標準庫還是用戶代碼中定義的? gcc和clang都給出了一致的行爲。

編譯器不知道用戶代碼與標準庫中的用戶代碼之間的區別。雖然編譯器可以區分標準庫文件和用戶代碼,但我真的沒有看到有任何理由這麼做。它看到的只是文本數據,它可以lex/parse/codegen。

+0

這並沒有真正回答這個問題。 – cnicutar 2013-03-10 21:03:33

+0

@cnicutar我正在編輯答案來回答這個問題:-) – 2013-03-10 21:03:55

+0

@aniket我的gcc版本是4.7.2。和鏗鏘有3.0版本。如果我取消2號線和3號線的註釋,他們都會抱怨。 – 2013-03-11 14:22:34