2016-09-28 3 views
3

私はすでにCやC++のどちらの変数名も表示できないことを知っていますが、これは他のStackOverflow投稿にも言及されています。オブジェクトの名前を印刷することはできますか?

しかし、Delphiのような他の言語では、オブジェクトのクラス名を印刷することができます。これがC++で可能かどうかはわかりません。

私の質問:それはオブジェクトのオブジェクト名を印刷することは可能ですか?

背景:私はSTLベクトルを使用して位置と値(別々のベクトルの両方)を追跡するプログラムを作成していますが、オブジェクト名の前にベクトルの内容を印刷したい私が場所を見ているのか、値を見ているのか分かります)。

を使用でき
+4

オブジェクト名またはオブジェクトタイプ名? –

+0

C/C++で変数の名前を表示できないことは完全には正しくありません。実際には、プリプロセッサを使って行うことができます: '#define VAR_TO_STRING(VAR)#VAR' –

+0

オブジェクト名をください。 – Dominique

答えて

6

typeid(someObject).name(); 

しかし、戻り値は実装定義であるとのすべての有用なまたは読み出し可能な何かを返す必要はありません。

タイプ定義名のヌル終了文字列 を実装して返します。 では特に返される文字列はいくつかの型で同一であり、同じプログラムの呼び出し間では が変更されるという保証はありません。

だから、単にロギング以上のものが必要な場合は、自分で追跡することをお勧めします。

さらに詳しい情報:.name()

0

あなたはここに

#include <typeinfo> 
typeid(object).name() 

を使用することができ、同じのための作業コードである -

#include <iostream> 
#include <typeinfo> 
using namespace std; 

class Adi { 
int a; 
int b; 
}; 

int main() { 
Adi obj, obj2; 
cout << typeid(obj2).name() << endl; 
return 0; 
} 

出力: 3Adi

出力形式は、その続くクラス名の長さです名。

4

これは私が使用するものです。

#include <cstddef> 
#include <cstring> 
#include <iostream> 
#include <ostream> 

    template < class T > 
    std::string type_name() 
    { 
#ifdef __clang__ 
     std::string p = __PRETTY_FUNCTION__; 
     return p.substr(43, p.length() - 43 - 1); 
#elif defined(__GNUC__) 
     std::string p = __PRETTY_FUNCTION__; 
#if __cplusplus < 201402 
     return p.substr(57, p.length() - 53 - 62); 
#else 
     return p.substr(46, p.length() - 46 - 1); 
#endif 
#elif defined(_MSC_VER) 
     std::string p = __FUNCSIG__; 
     return p.substr(38, p.length() - 38 - 7); 
#else 
     return std::string("This function is not supported!"); 
#endif 
    } 

それは通常タイプの人間に優しいバージョンを提供します。コンパイラ(およびバージョン)によっては、部分文字列が異なる場合があります。

Coliru例:http://coliru.stacked-crooked.com/a/bcdb77a7519136ea

+0

それはちょうど、*うわーです。 +1これから使うつもりです:) – Rakete1111

+2

使用されたコンパイラがこれらのどれでもない場合はどうなりますか?私は、 ''この関数はサポートされていません」という返値で '#else'を追加します。 – xinaiz

0

プリプロセッサを使用して、変数の名前を印刷することが可能である:

#define STRINGIFY(a) #a 
#define VAR_NAME(a) STRINGIFY(a) 

int my_var = 42; 
std::cout << "var name = " << VAR_NAME(my_var) << std::endl; 

テンプレートクラスのオーバーロードを使用することができ、クラスの名前を取得し、名前を取得するタイプごとに、このクラスの部分的な特殊化を実装するだけで済みます。すべてのPODの種類とSTLコンテナ用

template< typename T> class type 
{ 
public: 
    static constexpr const char* name() { 
     return "unknown"; 
    } // end type< T>::name 
}; // type< T> 

template<> class type< int> 
{ 
public: 
    static constexpr const char* name() { 
     return "int"; 
    } 
} 

template<> class type< std::string> 
{ 
public: 
    static constexpr const char* name() { 
     return "std::string"; 
    } 
} 

std::cout << "type name = " << type< int>::name() << std::endl; 

このようなクラスや専門分野、ここで提供されています: https://github.com/Gemini67/Celma

は、変数の型名を取得するためにも解決策が含まれています。

関連する問題