Reputation: 11
I'm having a problem with overloading of a function that gets a template as an input. I made a template vector:
template TempVec<class T, int size>
which has two options: vector of int by size 3, or vector of complex by size 2.
I have a function called InnerProduct
that gets two vectors and returns the result of the inner products between the vectors. The problem is that the type of the return value depends on the vector type (int
/complex
).
So I created these three functions (in the class of TempVec):
template <class T, int size>
friend int InnerProduct(const TempVec<T, 3>& v1, const TempVec<T, 3>& v2);
template <class T, int size>
friend complex InnerProduct(const TempVec<T, 2>& v1, const TempVec<T, 2>& v2);
template <class T, int size>
friend TempVec<T, size> InnerProduct(const TempVec<T, size>& v1, const TempVec<T, size>& v2);
When I call InnerProduct
, I always get to the last function (the most general function), even if I pass two vectors of size 3, or two vectors of size 2. I tried to get rid of the last function, but I got the error:
'InnerProduct': none of the 2 overloads could convert all the argument types.
I would be very grateful for some explanation/solution to the problem.
Upvotes: 0
Views: 90
Reputation: 48918
The first 2 overloads can never ever be taken (without being explicit), because the compiler can't deduce size
, and so SFINAE kicks in and the overloads are discarded.
The compiler can't deduce size
because you never specify it in the function signature. size
is completely redundant in the 2 overloads possibly (I don't know the body), but the compiler has to initialize it. Because it can't deduce it from the signature, you have to specify it yourself. If you don't, they will never get chosen.
If you remove the third one, of course you'll get an compiler error, because the first 2 overloads can't be chosen if you don't specify a size
yourself.
Just remove size
, you don't need it:
template <class T>
friend int InnerProduct(const TempVec<T, 3>& v1, const TempVec<T, 3>& v2);
template <class T>
friend complex InnerProduct(const TempVec<T, 2>& v1, const TempVec<T, 2>& v2);
Upvotes: 1