GCCのtype_infoのname()は、name manglingされたままの文字列を返す。読みにくいこと極まりない。
しかたがないので、Demanglingしてやることにする。
#include <cxxabi.h> class Demangle { private : char * realname ; public : Demangle( std::type_info const & ti ) { int status = 0 ; realname = abi::__cxa_demangle( ti.name(), 0, 0, &status ) ; } Demangle( Demangle const & ) = delete ; Demangle & operator = ( Demangle const & ) = delete ; ~Demangle() { std::free( realname ) ; } operator char const * () const { return realname ; } } ;
以下のように使う。
struct Foo {} ; int f( float, int, Foo *, Foo &, Foo const volatile * (&) [10] ) ; template < typename ... Args > struct Bar { } ; int main() { std::cout << Demangle(typeid(int)) << std::endl ; std::cout << Demangle(typeid(float)) << std::endl ; std::cout << Demangle(typeid(Foo)) << std::endl ; std::cout << Demangle(typeid(f)) << std::endl ; std::cout << Demangle(typeid(Bar<int, char, float, Foo, Bar<char, int, long> >)) << std::endl ; }
出力結果
int float Foo int ()(float, int, Foo*, Foo&, Foo const volatile* (&) [10]) Bar<int, char, float, Foo, Bar<char, int, long> >
とりあえず、Variadic Templatesについて、だいぶ理解した。やはり、実際に動くコンパイラで、書いて試すことができるというのは、ありがたい。
おおーっ、こりゃええですな!
ReplyDeleteせやろ、せやろ。
ReplyDeleteていうかな、gccはんのtype_info::name()が、ハナッからdemanglingした結果を返したったらえーねん。
なんでmanglingしたまま、よこすねん。アホちゃうか。
$ nm object.o | c++filt
ReplyDelete$ objdump -t object.o | c++filt
とかのように、typeidをcoutに出した結果をc++filtにパイプしてやればよいと思います。
別のDemangle変数に代入したらメモリリークですな
ReplyDelete>別のDemangle変数に代入したらメモリリークですな
ReplyDelete修正
void operator=(Demangle const &) = delete; も追加で。
ReplyDeleteこれはいいな
ReplyDelete知っておこう