2012-08-28 90 views
7

是否有任何保證函數的區別僅在於它的名稱(不是參數和返回類型)不能在C和C++中共享相同的地址?我沒有看到標準中的任何內容。幾個函數的指針

#include <cassert> 

void foo() {} 

void bar() {} 

int main() 
{ 
    assert(foo != bar); 
} 

回答

7

的C++ 11標準說

5.10相等運算
相同類型(指針轉換之後) 指針可以比較平等。當且僅當它們都爲空,都指向相同的函數,或者兩者都代表相同的地址(3.9.2)時,相同類型的兩個指針才相等。

如果你沒有任何指向函數的指針,它們可能只有相同的地址,但我們不知道。如果你比較兩個不同函數的指針,它們不能相等。混淆


一個原因可能是,MSVC編譯器是已知的用於這種情況發生,以產生對不同類型的相同的機器代碼(如intlong)模板功能組合的代碼。這不符合規定。

但是,這是與不同的功能簽名,而不完全是這個問題。

+0

最後的評論現在沒有意義。對於不同的參數類型,您有不同的函數指針,所以關於「相同類型的兩個[函數]指針」的規則不再適用。 – MSalters

+0

的確如此。這更多的是關於我們已經看到不同的功能*可以得到相同地址的情況,但不是真正問到的問題, –

1

實施細節。

(C99,5.1.2.3p1)「本國際標準中的語義描述描述了優化問題無關的抽象機器的行爲。」

+0

該報價是真實的。問題是關於一個真正的編譯器,它與抽象機器不同,但它(即使在優化的情況下)必須顯示與允許的抽象機器相同的可觀察行爲。 – MSalters

3

是的。 6.5.10 C99:6

兩個指針比較相等當且僅當兩者都是空指針,兩者 是指向同一對象(包括一個指向對象和 一個子對象在其開始)或功能,...

編輯:段其餘部分,因爲它原來是有一定的重要性:

都是指向一個過去相同數組 對象的最後一個元素的指針,或者一個是指向一個指針的指針,超過一個數組對象的末尾 ,另一個指向不同數組對象的起始指針 恰好在 地址空間中的第一個數組對象之後。

我從它是什麼:應用到錯誤的操作數是,在這麼多的話,不確定

  • 平等。這可能是由於外部原因導致的意外情況,但在使用錯誤時未明確定義,因此在使用錯誤時未定義<
  • 盡我所知,段落的其餘部分不適用於函數,因爲函數既不是對象也不能是數組的元素。
+0

那麼不應該保證它們實際上是相同的功能嗎?我的意思是,編譯器對此進行了優化,但語言規範函數與後編譯彙編函數看起來不同。 –

+0

來自Bo的回答,最後一部分是「或者兩者都代表相同的地址」。這個報價的最後部分是否相似? –

+0

@DanielSloof我認爲這取決於'...'後面的內容。 –

2

開啓優化的許多編譯器將使兩個函數具有相同的地址。例如,來自msdn

/OPT:ICF 可能導致在相同的地址被分配給不同的功能 或只讀數據成員(具有 /戈瑞編譯常量變量)。所以,/ OPT:ICF可以破壞一個程序,這個程序取決於函數 或只讀數據成員的地址是不同的。請參閱/ Gy(啓用 函數級鏈接)瞭解更多信息。

ICF:相同代碼摺疊