¿Por qué el compilador no resuelve esta llamada a una función de plantilla?
-
01-10-2019 - |
Pregunta
En el programa a continuación, ¿por qué el compilador genera un error durante la llamada a la función de plantilla printMax
y no a la llamada a la función printMaxInts
?
#include <iostream>
template<class A>
void printMax(A a,A b)
{
A c = a>b?a:b;
std::cout<<c;
}
void printMaxInts(int a ,int b)
{
int c = a>b?a:b;
std::cout<<c;
}
int main()
{
printMax(1,14.45);
printMaxInts(1,24);
}
Solución
Para que el compilador para deducir la A
parámetro de plantilla a partir de los argumentos que se pasan a la plantilla de función, ambos argumentos, a
y b
debe tener el mismo tipo.
Sus argumentos son de tipo int
y double
, por lo que el compilador no puede deducir qué tipo se debe utilizar realmente para A
. A
debe ser int
o debe ser double
?
Se puede solucionar este problema haciendo que ambos argumentos tienen el mismo tipo:
printMax(1.0, 14.45);
o especificando explícitamente el parámetro de plantilla:
printMax<double>(1, 14.45);
La razón de que la llamada a la función de plantilla no se puede llamar es que el compilador no tiene que deducir el tipo de los parámetros: sepa el tipo de los parámetros, ya que usted ha dicho lo que eran en la declaración de función:
void printMaxInts(int a, int b)
Tanto a
y b
son de tipo int
. Cuando se pasa una double
como argumento para esta función, la conversión estándar double -> int
se lleva a cabo en el argumento y la función se llama con el int
resultante.
Otros consejos
El siguiente código se basa en la respuesta de James. Se dará cuenta de que he tomado la expresión condicional:. He hecho esto porque las cláusulas de resultado a que la expresión deben ser del mismo tipo, que impone una restricción adicional sobre A y B
Los únicos requisitos en A y B en esta versión del código es que hay un operador <() que ellos relacionados (o uno se puede convertir en el otro), y la existencia de las funciones de operador requisito << ().
template<typename A, typename B>
void printMax(A a, B b)
{
if (a < b)
{
cout << b;
}
else
{
cout << a;
}
}