Reputation: 12896
The following code can be build successfully.
#include <iostream>
#include <string>
using namespace std;
template <class T>
struct Foo
{
template <class S>
void print(const T& t, const S& s);
};
template <>
struct Foo<int>
{
template <class S>
void print(const int& t, const S& s)
{
cout << s << " " << t << endl;
}
};
int main(void)
{
string str("hello");
Foo<int> foo;
foo.print(7, str);
return 0;
}
But if I move the definition of the member function Foo<int>::print(...)
outside the definition of the class Foo<int>
like below
template <>
template <class S>
void Foo<int>::print(const int& t, const S& s)
{
cout << s << " " << t << endl;
}
I got a GCC compiling error like this:
error: too many template-parameter-lists
void Foo<int>::print(const int& t, const S& s)
^
Where did I make a mistake?
Upvotes: 1
Views: 2507
Reputation: 137315
§14.7.3 [temp.expl.spec]/p5:
Members of an explicitly specialized class template are defined in the same manner as members of normal classes, and not using the
template<>
syntax. The same is true when defining a member of an explicitly specialized member class. However,template<>
is used in defining a member of an explicitly specialized member class template that is specialized as a class template.
print
is not a class template. Hence, remove the template <>
:
template <>
struct Foo<int>
{
template <class S>
void print(const int& t, const S& s);
};
template <class S>
void Foo<int>::print(const int& t, const S& s)
{
cout << s << " " << t << endl;
}
Demo.
Note that if you do not explicitly specialize Foo<int>
, but tries to define Foo<int>::print
directly, then you are explicitly specializing a member of a particular implicit instantiation of Foo
, and not defining a member of an explicit specialization. For that, you need template <>
:
template <class T>
struct Foo
{
template <class S>
void print(const T& t, const S& s);
};
template <>
template <class S>
void Foo<int>::print(const int& t, const S& s)
{
cout << s << " " << t << endl;
}
Upvotes: 4