2011-03-08 22 views
2

我已經搜索並且無法驗證在.h文件中聲明並且定義在.cpp文件中時GCC編譯器如何處理內聯getter和setter。在.h和.cpp文件中分隔定義和聲明時,是否可以內聯getter和setter?

大多數人似乎都說GCC無法看到這些源文件障礙,並且根本無法將這些內聯內聯,而其他人則不同意。我查看了文檔,也找不到答案。我錯過了嗎?

我知道內聯是由編譯器做出的選擇,並不總是有保證,但假設最佳情況,至少可以嗎?

回答

5

(你的真正用意是什麼要問的是哪裏的定義是不同的.cpp文件到您當前正在編制一個情況,再後來在鏈接,編譯器不關心.hpp.cpp, 。但對translation units

無論如何,在http://gcc.gnu.org/onlinedocs/gcc/Optimize-Options.html,向下滾動到 「flno」:

這個選項運行標準的鏈接時優化。 GCC的前兩個調用將把GIMPLE的字節碼錶示保存到foo.o和bar.o中的特殊ELF部分。最後的調用將讀取foo.o和bar.o中的GIMPLE字節碼,將這兩個文件合併爲一個內部圖像,然後照常編譯結果。由於foo.o和bar.o都合併爲一個圖像,因此這會導致GCC中的所有程序間分析和優化在兩個文件中工作,就好像它們是單個文件一樣。這意味着,例如,內聯將能夠將bar.o中的函數內聯到foo.o中的函數中,反之亦然。

所以,是的,可以跨模塊邊界優化內聯。

然而,C++仍然使得其要求:

內聯函數應每翻譯單元在其中使用它來限定。 [3.2/3,C++ 03]

所以其實你可能不會編寫代碼,如果你使用的inline關鍵字來利用這一點;你只能依賴鏈接器「只是決定」在適合的情況下內聯你的函數。所以這不是一個可以讓你移動代碼的選項。

請記住,在你的代碼中寫入inline與函數實際上沒有一對一的關係,實際上得到物理內聯;這只是編譯器(或鏈接器,如果你已經打開了上面提到的鏈接時優化)的暗示。

+0

是的,這就是我的意思。謝謝你的糾正。這是我似乎忽略的一個區別。 – Nathan 2011-03-08 16:43:29

+0

@Nathan:沒問題 – 2011-03-08 16:47:16

0

1 /在內部聲明的函數必須在所有使用它們的編譯單元中定義

2 /假設參數是正確的,gcc總是能夠內聯函數,只要它看到定義,它們就不需要聲明爲內聯。 (但是聲明它們內聯將有助於使定義在所有編譯單元中可用,並且您可能需要更高級別的優化來內聯未聲明內聯的函數。)

3 /最近版本的gcc有可能做鏈接時間優化。 IIRC,鏈接時可能的優化之一是內聯。