天天看點

C語言函數隐式聲明——implicit declaration warning

implicit declaration of function——函數隐式聲明警告

原因:

1、該函數未被聲明,但卻被調用了,此時gcc會報這樣的警告資訊。

2、(網友總結)該函數所在源檔案沒有被編譯為.o二進制檔案。

解決辦法:

1、在調用之前先聲明這個函數,一般使用extern關鍵字(該關鍵字非必需)

   聲明函數可以不加extern,函數預設extern;聲明變量必須要加extern。

2、将該函數聲明在頭檔案中,然後在要調用的檔案中包含該頭檔案

3、在c99、c11标準中,這被當做錯誤處理,而不是僅僅是警告。

根本原因:c語言中函數的隐式聲明

在c語言中函數聲明不是必須的,即使沒有聲明函數,gcc編譯器也隻是會提示警告。但是函數聲明卻是很有必要的。

那麼函數聲明到底有聲明作用呢?

其實函數聲明的作用是讓編譯器幫你檢查函數調用時有沒有錯誤。比如參數的數量是否正确,如果調用函數時候少傳入一個參數,并且沒有聲明該函數,編譯器無法知道你調用是否正确,隻會提示一個警告。很多人會忽略警告,導緻最後程式運作時出現異常。

為什麼如果不聲明函數,編譯器發現不了錯誤?

編譯器在編譯過程中依次生成與源檔案對應的可重定位目标檔案(.o),每個源檔案中調用的函數在連結前都是以符号的形式展現在.o檔案中。在編譯過程中不會去檢查某個函數的形式,因為函數參數是通過寄存器和壓棧來處理的,直接把函數翻譯成符号,編譯器是不知道關于函數參數的資訊的,最後交給連接配接器把符号翻譯成位址。是以連結的時候隻要能找到對應得符号就不會報錯。

從現代C語言的角度來說,任何辨別符(除了goto的label以及main()的main)在使用之前都一定要聲明,函數也是如此。

理論上這是必須的,但某些編譯器為了遷就以前代碼的一些寫法放松了這個要求。是以還是應該寫,盡管看起來貌似不是必須的。

--------------------- 

Implicit function declarations in C.

It should be considered an error. But C is an ancient language, so it's only a warning. Compiling with -Werror (gcc) fixes this problem. When C doesn't find a declaration, it assumes this implicit declaration: int f();, which means the function can receive whatever you give it, and returns an integer. If this happens to be close enough (and in case of printf, it is), then things can work. In some cases (e.g. the function actually returns a pointer, and pointers are larger than ints), it may cause real trouble. 

Note that this was fixed in newer C standards (C99, C11). In these standards, this is an error. However, gcc doesn't implement these standards by default, so you still get the warning.

GCC隻是預設還允許implicit function declaration功能而已,較新的C規範(C99、C11)是不允許不聲明直接用的。

繼續閱讀