2012-02-22 149 views
0

在下面的代碼似乎容器的可變參數模板版本不繼承的容器的單一模板版本的名稱函數g ++ 4.5.2抱怨:類具有可變參數模板成員函數繼承

no matching function for call to 」Container<Variable1, Variable2>::name(Variable2)」 
candidate is: std::string Container<First_Variable, Rest ...>::name(First_Variable) [with First_Variable = Variable1, Rest = {Variable2}, std::string = std::basic_string<char>] 

代碼:

#include "iostream" 
#include "string" 

using namespace std; 

struct Variable1 { 
    string operator()() { 
     return string("var1"); 
    } 
}; 

struct Variable2 { 
    string operator()() { 
     return string("var2"); 
    } 
}; 

template<class... T> class Container; 

template<class First_Variable, class... Rest> 
class Container<First_Variable, Rest...> : public Container<Rest...> { 
public: 
    string name(First_Variable variable) { 
     return variable(); 
    } 
}; 

template<class Variable> class Container<Variable> { 
public: 
    string name(Variable variable) { 
     return variable(); 
    } 
}; 

int main(void) { 
    Container<Variable1, Variable2> c; 
    cout << "Variables in container: " << c.name(Variable1()) << ", " << c.name(Variable2()) << endl; 
    return 0; 
} 

什麼我做錯了,或者這甚至應該工作?

回答

2

name隱藏了基類的名稱。嘗試

template<class... T> class Container; 

template<class First_Variable, class... Rest> 
class Container<First_Variable, Rest...> : public Container<Rest...> { 
public: 
    using Container<Rest...>::name; 

    string name(First_Variable variable) { 
     return variable(); 
    } 
}; 

template<class Variable> class Container<Variable> { 
public: 
    string name(Variable variable) { 
     return variable(); 
    } 
}; 

如果你是迂腐的,那麼你的部分專業化是不正確的。 C++ 11規範對形式爲<FixedParameter, Pack...><FixedParameter>的表單模糊不清的兩個部分專業化。討論過這個問題,許多人感到驚訝,因此一些編譯器不實現C++ 11的那部分內容。

+0

謝謝!至少g ++到4.7-20120211和clang ++ 3.0不會抱怨與剽竊。有沒有其他方法可以實現這一點,還是我不得不依賴編譯器不嚴格執行此操作? – user1226313 2012-02-22 18:11:45

+0

@user你可以專注於'和''。但我認爲你的代碼不會被編譯器拒絕。所以我可能會保持原樣。 – 2012-02-22 18:17:28