2010-04-28 14 views
10
template <class T> 
void max (T &a ,T &b) 
{}//generic template #1 

template<> void max(char &c, char &d) 
{} //template specializtion #2 

void max (char &c, char &d) 
{}//ordinary function  #3 

¿cuál es la diferencia entre 1, 2 y 3?¿cuál es la diferencia entre la especialización explícita de plantilla y la función normal?

+1

No puede especializar plantillas de funciones, el efecto sería el mismo que las sobrecargas normales. – AshleysBrain

+5

@AshleysBrain: Eso está mal. Puedes especializar plantillas de funciones. Usted no puede hacer especializaciones parciales. – sbi

+0

Ooh, eso es lo que quise decir. Gracias. – AshleysBrain

Respuesta

10
  1. es una función de plantilla
  2. es una especialización total de la función de plantilla anterior (no sobrecarga!)
  3. es una sobrecarga de la función

Aquí está un extracto de C++ Coding Standards: 101 Rules, Guidelines, and Best Practices :

66) No se necesitan plantillas de función

Especializaciones de plantilla de funciones Nunca participe en sobrecargas: por lo tanto, las especializaciones que escriba no afectarán la plantilla que se utilice, y esto va en contra de lo que la mayoría de la gente esperaría intuitivamente. Después de todo, si hubiera escrito una función no explícita con la firma idéntica en lugar de una especialización de plantilla de función, la función no característica siempre se seleccionaría porque siempre se considera que es una mejor coincidencia que una plantilla.

El libro le aconseja añadir un nivel de direccionamiento indirecto mediante la implementación de la plantilla de función en términos de una plantilla de clase:

#include <algorithm> 

template<typename T> 
struct max_implementation 
{ 
    T& operator() (T& a, T& b) 
    { 
    return std::max(a, b); 
    } 
}; 

template<typename T> 
T& max(T& a, T& b) 
{ 
    return max_implementation<T>()(a, b); 
} 

Ver también:

+0

acabo de corregir los errores ortográficos en el código, perdón por ese –

+0

enlaces de getw añadidos, los mismos que los proporcionados por @Michael –

+0

gracias entendí el punto :) – Suri

2

Las reglas de coincidencia para los parámetros de la plantilla difieren sutilmente de las funciones sobrecargadas. Un ejemplo de lo que difiere pueden verse cuando se intenta invocar max() con argumentos de diferentes tyoes:

max(1,'2'); 

Esto coincidirá con la función sobrecargada, pero ni la plantilla de base ni la especialización.

+0

En mi lectura inicial del código, no veo diferencia en las firmas entre la sobrecarga y la especialización, otras que la plantilla ¿Por qué, entonces, 'max (1, '2')' no se correspondería con la especialización? Más específicamente, ¿por qué es '1', un' int', convertido a 'char' en el caso de sobrecarga pero no en el caso de especialización? – rcollyer

+0

@rcollyer: Ver la cita * # 66 * en la respuesta de Gregorys. –

+0

@rcollyer: La respuesta simple es: _Porque el estándar dice que sí ._ 'template <> void max (...)' es la sintaxis de una plantilla __specialización__; 'void max (...)' es la sintaxis de una función __overload__. Las reglas para hacer coincidir las funciones sobrecargadas son diferentes de las reglas para las especializaciones de plantilla coincidentes. (Y las sobrecargas se eligen _primero_ y solo si se elige una plantilla, se consideran posibles especializaciones). Por qué elegir sobrecargas es mucho más relajado que elegir especializaciones, no puedo decirlo. Pero supongo que, si las reglas para las sobrecargas se convirtieran en _now_, también serían más estrictas. – sbi

Cuestiones relacionadas