2012-03-26 26 views
3

我有以下代碼,使用g ++ 4.4.6可以正常工作,但無法使用Visual Studio 2008進行編譯。它似乎與參數依賴查找有關,所以我認爲g ++是正確的。using指令如何影響C++中的函數參數?

// testClass.hpp 
namespace test { 
    class foo { 
     public: 
     foo(){} 
    }; 

    class usesFoo { 
     public: 
     usesFoo() {} 

     void memberFunc(foo &input); 
    }; 
} 

// testClass.cpp 
#include "testClass.hpp" 

using test::usesFoo; 

void usesFoo::memberFunc(foo &input) { 
    (void) input; 
} 

在Visual Studio編譯時,我得到的錯誤,

1>正在編譯...
1> testClass.cpp 1> C:\工作\ testproject \ testproject \ testclass.cpp (6):error C2065:'foo':未聲明的標識符 1> c:\ work \ testproject \ testproject \ testclass.cpp(6):error C2065:'input':未聲明的標識符 1> c:\ work \ testproject \ testproject \ testclass.cpp(6):error C2448:'test :: usesFoo :: memberFunc':函數式初始化器似乎是函數定義

我意識到將命名空間直接放在cpp文件中的成員函數上,或者「using namespace test」會解決這個問題,我更加好奇這個標準所說的是什麼。

+1

我沒有看到任何理由期望您的代碼編譯; foo沒有在usesFoo中定義。這很有趣,它用g ++編譯。 – 2012-03-26 20:57:36

+2

'memberFunc'不是靜態的,'foo'不合格。 *參數*依賴查找意味着*函數*的名稱在參數的名稱空間中查找,而不是相反。 – 2012-03-26 20:57:52

+0

+1 – 2012-03-26 21:06:49

回答

1

該代碼是正確的,但它與查詢依賴查找無關。另外,使用聲明僅影響usesFoo而不是foo的查找:一旦您發出了類成員的名稱,就會在該類的上下文中查找其他名稱。由於foo是test :: usesFoo的成員。如果沒有使用指令你需要這樣定義的成員函數:

void test::usesFoo::memberFunction(foo& input) { 
    (void)input; 
} 

此相關的條款是3.4.1不合格的名稱查找[basic.lookup.unqual]第6款:

函數聲明符id後面的函數定義中使用的名稱是名稱空間N的成員(其中,僅用於說明的目的,N代表全局作用域)應在其用於在其使用的塊或其封閉塊(6.3)之一中,或者應在其用於名稱空間N之前進行聲明,或者如果N是嵌套名稱空間,則應在其使用之前聲明爲其中一個N包含名稱空間。

僅當函數被調用時纔會進入圖片,而不是在定義函數時進入圖片。這些東西根本就沒有任何關係。

相關問題