2011-03-24 116 views
1

您好我嘗試在VC建立一個tamplate功能++象下面這樣:錯誤:C++模板函數

template<class _Fn0,class _Fn1> void for_each(_Fn0 _Func0,_Fn1 _Func1) 
{  
    _Func0(12); 
    _Func1(12); 

} 

當我使用_Func0/1全局函數這項工作propely。

void aglobal(int a) 
{ 
    a++; 
} 
for_each(aglobal,aglobal); 

但是當我使用memeber類函數時,我收到錯誤消息。

class A 
{ 
public: 
    void aa(int a) 
    { 
     a++; 
    } 
    void bb(int b) 
    { 
     b++; 
    } 
    void cc() 
    { 
     for_each(&A::aa,&A::bb); 
    } 
}; 

錯誤C2064:術語不計算爲服用1個參數 1>見參考起作用模板實例 '無效的for_each(_Fn0,_Fn1)' 被編譯的功能。

我該如何解決這個錯誤?

謝謝herzl。

+1

請注意,以下劃線後跟大寫字母(如'_Fn0'或'_Func0')開頭的名稱會被保留​​,因此您不允許在代碼中使用它們。編譯器和標準庫實現通常在內部使用這些名稱。 – 2011-03-24 15:52:45

回答

9

A::aaA::bb是非靜態成員函數;你試圖稱他們爲非會員功能。

非靜態成員函數只能在對象的實例上調用。

要解決它,你可以

  1. 使aabb靜態的,或者

  2. 合格A一個實例爲for_each,以便它可以調用該實例上的功能,或

  3. 使用std::bind/std::tr1::bind/boost::bind在傳遞成員函數之前將成員函數綁定到實例到函數模板,或者

  4. 編寫一個函數,它存儲一個指向您要調用成員函數的實例的指針,並指向您要調用的成員函數的指針;這實際上是bind所做的(雖然bind更通用)。

+1

+1請注意,由下劃線開頭的名稱由實現保留。 – 2011-03-24 15:53:53

+0

@James謝謝你有使用std :: bind的例子嗎? – 2011-03-24 16:03:28

+0

@herzl:如果你想在'this'上調用這兩個成員函數:'for_each(std :: bind(&A :: aa,this,std :: placeholders :: _ 1),std :: bind(&A :: bb,this,std :: placeholders :: _ 1))' – 2011-03-24 16:13:15

1

該類的成員函數總是接受額外的參數「this」指針,所以你可以讓它們成爲靜態的來試試這個。