![](/img/trans.png)
[英]What's the difference between static inline, extern inline and a normal inline function?
[英]What happens with an extern inline function?
如果我將 .h 文件中的函數定義為
extern int returnaint(void);
在相關的 .c 文件中將其定義為
inline int returnaint(void) {
return 1;
}
並將標題包含在另一個 .c 文件中並使用該函數? 當我單獨編譯這些東西時,為每個 .c 文件創建一個目標文件然后鏈接它們,是否包含內聯函數,或者會發生什么?
我知道編譯器可以忽略inline
,但是如果在這種情況下它不忽略它呢?
將inline
添加到.c
文件中的函數定義只是多余的。
您的.c
文件的編譯單元會看到一個extern
聲明(沒有inline
)和一個inline
定義。 因此它發出目標文件中函數的符號。
所有其他編譯單元只看到一個extern
聲明,因此如果您將最終可執行文件與其他.o
文件鏈接,它們可以毫無問題地使用該函數。
事實上,你只是把它弄錯了。 此功能旨在用於您在.h
文件中具有inline
定義,所有人都可以看到的情況。 函數的這個定義只作為符號的聲明,就像extern
一樣,但沒有定義它。
僅在一個.c
文件(編譯單元)中的extern
聲明然后確保在那里定義符號。
術語有點混亂, inline
定義充當符號的聲明,而extern
聲明充當符號的定義
它不會編譯。 來自 C11 (ISO/IEC 9899:2011) §6.7.4功能說明符(強調):
任何具有內部鏈接的函數都可以是內聯函數。 對於具有外部鏈接的函數,以下限制適用:如果函數是用內聯函數說明符聲明的,則它也應在同一翻譯單元中定義。 如果翻譯單元中函數的所有文件范圍聲明都包含不帶 extern 的內聯函數說明符,則該翻譯單元中的定義是內聯定義。 內聯定義不為函數提供外部定義,也不禁止另一個翻譯單元中的外部定義。 內聯定義提供了外部定義的替代方案,翻譯器可以使用它來實現對同一翻譯單元中的函數的任何調用。 未指定對函數的調用是使用內聯定義還是外部定義。 140)
140)由於內聯定義不同於對應的外部定義以及其他翻譯單元中的任何其他對應內聯定義,因此所有具有靜態存儲持續時間的對應對象在每個定義中也是不同的。
另一個.c
文件僅從標題中獲取inline
函數的聲明,而不是定義,因此它違反了粗體規則。
編輯:
正如@Jens Gustedt 指出的那樣,我之前的解釋是錯誤的,因為在 OP 的問題中,該函數在頭文件中被聲明為非內聯:
extern int returnaint(void);
因此,另一個.c
文件會將其視為普通函數。
我們只是有一個類似的問題,僅在.c文件中保持內聯即可解決警告問題。 在具有和不具有函數定義的兩個文件中,也都發生了加速。 使用-o3標志進行編譯。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.