Comment comparer la signature de deux fonctions?

35

Existe-t-il un moyen de vérifier si deux fonctions ont la même signature? Par exemple:

int funA (int a, int b);
int funB (int a, int b);
float funC (int a, int b);
int funD (float a, int b);

Dans cet exemple, funAet funBest la seule combinaison de fonctions à renvoyer true.

Stefano Pittalis
la source

Réponses:

39

Essentiellement, vous voulez vérifier si les types de deux fonctions sont identiques:

std::is_same_v<decltype(funA), decltype(funB)>

Je n'appellerais pas cela «comparer les signatures», car, si je me souviens bien, le type de retour ne fait pas partie d'une signature (car il n'affecte pas la résolution de surcharge).

HolyBlackCat
la source
20
Un type de retour participe à la résolution de surcharge des pointeurs de fonction et fait partie de la signature des modèles de fonction .
Davis Herring
15

Vous pouvez vérifier le type de fonction avec decltypeet std::is_same. par exemple

std::is_same_v<decltype(funA), decltype(funB)>  // true

VIVRE

songyuanyao
la source
14

D'autres ont mentionné la solution en utilisant std::is_sameet decltype.

Maintenant, pour généraliser la comparaison d'un nombre arbitraire de signatures de fonction, vous pouvez effectuer les opérations suivantes

#include <type_traits> // std::is_same, std::conjunction_v

template<typename Func, typename... Funcs>
constexpr bool areSameFunctions = std::conjunction_v<std::is_same<Func, Funcs>...>;

et comparer autant de fonctions qu'une comme

areSameFunctions<decltype(funA), decltype(funB), decltype(funC)>

( Voir la démo en direct )


Ou pour moins de frappe (c'est-à-dire sans decltype), faites-le en fonction

template<typename Func, typename... Funcs>
constexpr bool areSameFunctions(Func&&, Funcs&&...)
{
   return std::conjunction_v<std::is_same<Func, Funcs>...>;
}

et appeler simplement par

areSameFunctions(funA, funB, funC) 

( Voir la démo en direct )

JeJo
la source
3

Autre possibilité non mentionnée: vous pouvez utiliser typeiddepuis typeinfoet ==:

#include <typeinfo>

if(typeid(funA) != typeid(funB))
    std::cerr << "Types not the same" << std::endl;
SS Anne
la source
GCC me donne error: non-constant condition for static assertion.
HolyBlackCat
1
@HolyBlackCat Ah, c'est RTTI. Je ne savais pas que ce n'était pas le cas constexpr. J'ai un exemple un peu meilleur maintenant.
SS Anne