2 votes

Rôle des paramètres par défaut des modèles dans la résolution des surcharges des modèles de classes (partiellement spécialisées)

Cette réponse explique le comportement du programme suivant :

template<typename A, typename B = int >
struct FirstWins {
    static constexpr int i = 1;
};
template<typename A>
struct FirstWins<A, float/* anything different from int */ > {
    static constexpr int i = 2;
};

template<typename A, typename B = int >
struct SecondWins {
    static constexpr int i = 1;
};
template<typename A>
struct SecondWins<A, int > {
    static constexpr int i = 2;
};

int main()
{
    typedef void Whatever_t;
    cout << FirstWins < Whatever_t >::i << endl;  // prints 1
    cout << SecondWins< Whatever_t >::i << endl;  // prints 2
    return 0;
}

Cependant, je ne trouve pas de référence réelle décrivant explicitement ce comportement et confirmant ainsi la réponse.

Je n'ai pas pu trouver sur cppreference.com une phrase confirmant que les arguments explicites des modèles sont préférés aux arguments par défaut.

Je soupçonne que ce n'est pas vraiment la règle. La règle est que chaque fois qu'il y a une spécialisation partielle du modèle correspondant aux arguments du modèle, cette spécialisation est toujours choisie par rapport à l'instanciation du modèle primaire. Est-ce correct ? (dans ce cas, les docs expliquent d'une manière ou d'une autre cette règle, mais là encore pas de manière explicite).

2 votes

Un paramètre par défaut fournit simplement un type lorsque le code ne le fait pas. Il n'a aucun effet sur la sélection de la spécialisation.

2 votes

Je pense que vous ne savez pas à quoi servent les arguments des modèles par défaut. Dans votre exemple, cela signifie simplement que FirstWins<X> se résout en FirstWins<X, int> . La sélection effective de la définition de FirstWins<X, int> se produit après la "substitution" de B pour int .

0 votes

@Holt : bien sûr, mais ma question porte en fait sur les points suivants SecondWins<X, int> . Dans ce cas, SecondWins<X, int> est préféré à SecondWins<X, =int> .

0voto

Jarod42 Points 15729
template<typename A, typename B = int >
struct S {
//...
};

Peut être considéré comme

template<typename A, typename B = int >
struct S;
// So S<A> is S<A, int>

// Primary template
template<typename A, typename B>
struct S
{
   //...
};

// Possible specialization as
template<typename A>
struct S<A, int>
{
   //...
};

alors, il est plus clair quelle instanciation utiliser.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X