I’m desperately trying to get my specializations working but still having non-compilable code due to deducing arguments to incorrect one. Note, that the errors are not about defining the templates but about applying irrelevant operation in wrong template implementation. The reduced example of code demonstrating the problem, is that:
struct Test { void Method() const {} };
template<typename T>
void Cmp(T _val) { _val > 1; }
template<>
void Cmp<const Test &>(const Test &_val) { _val.Method(); }
template<>
void Cmp<const char *>(const char *_val) { _val[2]; }
int main()
{
Test test1;
char test2[5];
Cmp(10); // ok, expected
Cmp(test1); // error in Cmp(T)?! but expecting to instantiate Cmp(const Test &)
Cmp(test2); // error in Cmp(T)?! but expecting to instantiate Cmp(const char *)
return 0;
}
I really don’t wish to use explicit calls like Cmp<const Test &>(test1) (that works) as AFAIK the compiler should be able to deduce the arguments automagically and the whole idea behind these specializations is dispatching Cmp calls transparently (in real code, I’m defining operators). Of course, by-value specialization Cmp<Test>(Test) works as expected but for large sophisticated non-POD class it’s just ridiculous to pass it by value.
Whatever fixes I try to apply the compiler just stubbornly refuses to pick the by-reference specialization using the general template instead. It seems I’m missing something important but I’m really run out of ideas why my approach doesn’t work and how I should construct code expressing such a simple concept from non-templated C++ world as passing classes by reference. Of course, Google proven to be utterly useless for this problem. ^_^ I tried GCC 4.2.1 and 4.4.6.
Here,
Tis deduced from the argument to beTest. It is not deduced to beconst Test&so your specialization is not a match, hence why the primary template is instantiated. You would need to make your specialization take aTestby value. With this declaration, the specialization is indeed used:Here,
Tis deduced to bechar*, notconst char*, so the specialization doesn’t match. You would need to specialize forchar*instead ofconst char*to match this. Alternatively, you can convert the argument toconst char*when making the call:All that said, why specialize at all when you can overload?
You really should avoid specializing function templates. It’s difficult and in most cases is just not worth the trouble.