Résolution de surcharge C ++, opérateurs de conversion et const

Dans ce cas

void f(int *); void f(const int *); ... int i; f(&i); 

la situation est assez claire – f (int *) est appelé, ce qui semble correct.

Cependant, si j’ai ceci (cela a été fait comme ça par erreur (*)):

 class aa { public: operator bool() const; operator char *(); }; void func(bool); aa a; func(a); 

L’opérateur char * () est appelé. Je ne peux pas comprendre pourquoi une telle voie de décision serait meilleure que d’aller à l’opérateur bool (). Des idées?

(*) Si const est ajouté au deuxième opérateur, le code fonctionne comme prévu, bien sûr.

Parce que pour les conversions définies par l’utilisateur avec un opérateur de conversion, la conversion du type renvoyé vers le type de destination (c’est-à-dire char* to bool ) est considérée après la conversion de l’argument d’object, c’est-à-dire la conversion de l’argument d’object a en paramètre d’object implicite. [over.match.best] / 1:

Étant donné ces définitions, une fonction viable F1 est définie comme étant une meilleure fonction qu’une autre fonction viable F2 si, pour tous les arguments i , ICS i ( F1 ) n’est pas une séquence de conversion plus mauvaise que ICS i ( F2 ) , puis

  • pour certains arguments j , ICS j ( F1 ) est une meilleure séquence de conversion que ICS j ( F2 ) ou, si ce n’est pas le cas ,

  • le contexte est une initialisation par conversion définie par l’utilisateur (voir 8.5, 13.3.1.5 et 13.3.1.6) et la séquence de conversion standard du type de retour de F1 au type de destination (c’est-à-dire, le type de l’entité en cours d’initialisation) est une meilleure séquence de conversion que la séquence de conversion standard du type de retour de F2 au type de destination .

Donc, comme le paramètre d’object implicite, qui est une référence, n’est pas une référence constante pour l’ operator char* , il s’agit d’une meilleure correspondance en fonction du premier point.

a étant une instance non-const de aa , l’opérateur de conversion non-const correspond mieux (exactement) que l’opérateur const (nécessite l’ajout de constness), même si les types de résultat ne correspondent pas.

Votre object “aa” n’est pas const, C ++ préfère donc la conversion non const.

Si vous faites “aa” const, l’opérateur de conversion const bool () sera utilisé.