我有一个类模板。在这个类模板中,我试图定义一个成员函数模板,它接受const_iterator
s 集合上的string
s。集合本身可以是任何类型的 StdLib 集合,但实际上它将是 avector
或 a list
。
由于集合可以是任何类型,所以我使用一个template-template
参数来指定集合类型。但是,它将始终是string
. 我希望模板参数推导起作用,这样我就不必在调用成员函数时指定集合类型。
SSCCE 中后面的代码类似于我的预期用例。
到目前为止,我已经为类定义(Live Demo):
template <typename Foo>
struct Gizmo
{
Foo mF;
Gizmo (Foo f) : mF (f) {};
template <template <typename> class Cont> void DoIt(
typename Cont <string>::const_iterator begin,
typename Cont <string>::const_iterator end)
{
stringstream ss;
ss << "(" << this->mF << ")\n";
const std::string s = ss.str();
copy (begin, end, ostream_iterator <std::string> (cout, s.c_str()));
}
};
类模板的实例化编译成功:
int main()
{
list <string> l;
l.push_back ("Hello");
l.push_back ("world");
Gizmo <unsigned> g (42);
}
然而,当我尝试利用论据推论(没有它,整个练习几乎毫无意义):
g.DoIt (l.begin(), l.end());
GCC 抱怨它无法推断出模板参数:
prog.cpp: In function ‘int main()’:
prog.cpp:34:28: error: no matching function for call to ‘Gizmo<unsigned int>::DoIt(std::list<std::basic_string<char> >::iterator, std::list<std::basic_string<char> >::iterator)’
g.DoIt (l.begin(), l.end());
^
prog.cpp:34:28: note: candidate is:
prog.cpp:16:49: note: template<template<class> class typedef Cont Cont> void Gizmo<Foo>::DoIt(typename Cont<std::basic_string<char> >::const_iterator, typename Cont<std::basic_string<char> >::const_iterator) [with Cont = Cont; Foo = unsigned int]
template <template <typename> class Cont> void DoIt(
^
prog.cpp:16:49: note: template argument deduction/substitution failed:
prog.cpp:34:28: note: couldn't deduce template parameter ‘template<class> class typedef Cont Cont’
g.DoIt (l.begin(), l.end());
最终,我真正关心的是能够DoIt
在string
. 集合的实际类型可以是vector
或list
,我不想指定模板参数,也不想基于容器重载。
我怎样才能让它工作?
请注意,我的实际用例将使用 C++03。欢迎使用 C++11 解决方案,但我只能接受 C++03 解决方案。