2009-04-25 6 views
17
class foo 
{ 
public: 
    void say_type_name() 
    { 
    std::cout << typeid(this).name() << std::endl; 
    } 
}; 

int main() 
{ 
    foo f;; 
    f.say_type_name(); 
} 

Au-dessus de code affiche P3foo sur ma machine ubuntu avec g ++. Je ne comprends pas pourquoi il est en train d'imprimer P3foo au lieu de seulement foo. Si je change le code commetypeid() retourne des caractères supplémentaires en g ++

std::cout << typeid(*this).name() << std::endl; 

imprime 3foo.

Des pensées?

Répondre

31

Parce que c'est un pointeur vers foo. Et foo a 3 caractères. Donc, il devient P3foo. L'autre a le type foo, alors il devient 3foo. Notez que le texte dépend de l'implémentation, et dans ce cas, GCC vous donne simplement le nom interne, tronqué.

Entrez ce nom mutilée dans le programme c++filt pour obtenir le nom non substantypés:

$ c++filt -t P3foo 
foo* 
+0

WOW! Intéressant. Deux autres questions .. 1 - C++ filt fait partie de la distribution gcc ou fait partie de LINUX? 2 - Y at-il un moyen d'obtenir le nom brouillé d'une méthode ou d'une classe? –

+0

C++ filt fait partie de binutils (le paquet où ld (le linker) et les autres petits utils comme readelf viennent aussi): http://www.gnu.org/software/binutils/ –

+5

il n'y a aucun moyen de faites cela en C++. Dans GCC, cependant, il y a une fonction exposée par l'ABI qui fait cela. C'est dans cxxabi.h et appelé __cxa_demangle. il suffit de passer le nom mutilé. Son interface suit cet ABI: http://www.codesourcery.com/public/cxx-abi/abi.html#demangler –

17

std::type_info::name() retourne une implémentation nom spécifique. AFAIK, il n'y a pas de moyen portable d'obtenir un "gentil" nom, bien que GCC has one. Regardez abi::__cxa_demangle().

int status; 
char *realname = abi::__cxa_demangle(typeid(obj).name(), 0, 0, &status); 
std::cout << realname; 
free(realname); 
+0

Merci pour ça! Ce fut une aide précieuse dans mon projet actuel. –

0

est-il une solution portable

solution serait de faire un modèle hack pour retourner tous les noms de type harcoded comme char*

quelle plate-forme n'avez pas #include <cxxabi.h>?

+1

Sans support particulier de la classe elle-même (comme la méthode 'whoami()'), n'importe quel "template hack" ne peut sortir qu'un type * static *, pas le * dynamic * (considérer un pointeur vers une classe de base polymorphe). –

+0

Qt fournit un mécanisme de réflexion très agréable avec son système metaobject. Je le recommande fortement. –

Questions connexes