2012-11-14 174 views
1

當使用靜態成員函數指針作爲模板參數,我得到了最新的VC++編譯器(2012年11月CTP)這個編譯錯誤好。 我在g ++(pointer to static member function is "invalid" as a template argument for g++)中查找了一些類似的錯誤,但是它明確指出參數無效。靜態函數有什麼不同?靜態成員函數指針作爲模板參數

因爲像<typename T_Ret, typename... T_Args, T_Ret(*)(T_Args...)>這樣的結構不能編譯,因爲其他尿素原因,我正在將函數投射到void(*)(void)

struct A 
{ 
    static int f1(int a, int b) 
    { 
     return a + b; 
    } 
}; 

int f2(int a, int b) 
{ 
    return a + b; 
} 

template <typename Sig, void(*fnc)(void)> 
struct wrapper; 

template <void(*fnc)(void), typename T_Ret, typename... T_Args> 
struct wrapper<T_Ret (T_Args...), fnc> 
{ 
    static bool apply() 
    { 
     // get some ints here 
     int a = 1; 
     int b = 2; 
     typedef T_Ret (fnc_ptr*)(T_Args...); 
     int res = ((fnc_ptr)fnc)(a, b); 
     // do smth with result 
     res; 
     return true; // or false 
    } 
}; 

int main() 
{ 
    bool res; 
    res = wrapper<decltype(A::f1), (void(*)(void))A::f1>::apply(); // error 
    res = wrapper<decltype(f2), (void(*)(void))f2>::apply(); // compiles ok 
    return 0; 
} 

編輯: 好吧,我縮小到decltype問題。 當我明確地寫出類型,一切正常:

res = wrapper<int(int, int), (void(*)(void))A::f1>::apply(); // compiles ok 
+0

你鑄造的功能呢?我認爲你不能這樣做。 – Wug

+0

就我所知,只要您在打電話之前將其恢復到正確的類型,您就被允許。 – Xarts

+0

這是對您的問題的簡化。你真正的問題是什麼? – Wug

回答

1

編輯: 看起來像是一個編譯器bug:http://channel9.msdn.com/Series/C9-Lectures-Stephan-T-Lavavej-Core-C-/STLCCSeries6#c634886322325940618

解決方法:

變化decltype(A::f1)decltype(&A::f1)從而改變它的輸出從int(int, int)int (__cdecl *)(int,int)。並改變

template <void(*fnc)(void), typename T_Ret, typename... T_Args> 
struct wrapper<T_Ret (T_Args...), fnc> 

template <void(*fnc)(void), typename T_Ret, typename... T_Args> 
struct wrapper<T_Ret (*)(T_Args...), fnc> 

工作代碼:

struct A 
{ 
    static int f1(int a, int b) 
    { 
     return a + b; 
    } 
}; 

template <typename Sig, void(*fnc)(void)> 
struct wrapper; 

template <void(*fnc)(void), typename T_Ret, typename... T_Args> 
struct wrapper<T_Ret (*)(T_Args...), fnc> 
{ 
    static bool apply() 
    { 
     // get some ints here 
     int a = 1; 
     int b = 2; 
     typedef T_Ret (*fnc_ptr)(T_Args...); 
     int res = ((fnc_ptr)fnc)(a, b); 
     // do smth with result 
     res; 
     return true; // or false 
    } 
}; 

int main() 
{ 
    bool res; 
    res = wrapper<decltype(&A::f1), (void(*)(void))A::f1>::apply(); 
    return 0; 
} 
0

你可以嘗試像this

#include <iostream> 

using namespace std; 

struct A 
{ 
    static int f1(int a, int b) 
    { 
     return a + b; 
    } 
}; 

int f2(int a, int b) 
{ 
    return a + b; 
} 

template <typename T, T X> 
struct wrapper 
{ 
    template <typename... Args> 
    static bool value(Args... blargs) 
    { 
     return X(blargs...) == 3; 
    } 
}; 

int main() 
{ 
    bool res; 
    res = wrapper<decltype(&A::f1), &A::f1>::value(1,2); 
    cout << res << endl; 
    return 0; 
} 

但嚴重的是,這是容易得多:

#include <iostream> 

using namespace std; 

int main() 
{ 
    bool res; 
    res = A::f1(a, b) == 3; 
    cout << res << endl; 
    return 0; 
} 
+0

我希望我可以做到這一點更好(或更少boilerplatey)。但是我不會調用函數,我會通過函數指針註冊它,然後它將被Lua調用。所以函數只需要一個參數就具有特定的簽名(我的參數將通過Lua棧)。在這一點上,我想我只是好奇爲什麼自由函數和靜態類函數的行爲完全不同。 – Xarts

+0

他們不是。發佈更多代碼 – Wug

相關問題