2011-12-26 15 views
0

私は標準のマップ構造のキーとしてクラスを使用しようとしています。C++ - クラス名をstd :: mapのキーとして使用する方法はありますか?

使用方法は以下のとおりです。

std::map<ClassName, int> someMap; 

someMap[ StudentClass ] 
someMap[ TeacherClass ] 

このテンプレートファクトリクラスを使用します。

+0

[クラスの型をC++のクラスのインスタンスにマップするにはどうすればいいですか?](http://stackoverflow.com/questions/8562994/how-can-i-map-class-types-to-instances -of-that-c​​lass-in-c) – Omnifarious

+0

この質問はさまざまな形でポップアップし続けます。私はここ数ヶ月で少なくとも3回見ました。 – Omnifarious

答えて

4

あなたは人間が救済できるクラス名が必要ですか?そうでない場合は、typeidtype_infoを使用できます。 type_info::name()details)で文字列を取得できますが、そのことについては何も読み取ることも、一意であることも保証されていないことに注意してください(ただし、type_infoオブジェクト自体は一意になります)。それ以外にも、移植不可能なメカニズムに頼るか、これを行うための独自のコードを書く必要があります。

+2

"何も読めるものであることが保証されていない"とは少し問題を控えめにしています - 単純に '[NUL]'であってもよいし、別個の型に対しても同じことが許されています。 –

+1

Tonyは正しいですが、 'name'が提供するものの要件はありません。これを軽減するには、 'type_info'自体をキーとして使うだけです。これは、型に自然順序付けを提供する 'before'関数を持っています。 –

+0

コメントありがとうございます。私は答えを修正した。 –

1

これは、Microsoft固有のようなものだが、私はあなたが__uuidofを使用できると思う:

std::map<GUID, int> someMap; 
someMap[__uuidof(StudentClass)] = 1; 
someMap[__uuidof(TeacherClass)] = 2; 
someMap[__uuidof(ClassClass)] = 3; 

あなたがC++の仮想クラス変数またはそのような何かを使用してこれを行うことが良い方法はおそらくあります。

+0

'typeid'や' std :: type_info :: name'を使わないのはなぜですか? – Begemoth

+0

私は分かりません。 –

2

ベスト・ベットは、typeid()です。それはあなたにクラス間の一意性を与えます。ただし、typeidからクラス型を自動的に取り出すことはできません。

0

typeid(SomeObject).name()を使用できますが、コンパイラ間では移植できません。あなたが開発しているものがライブラリや移植可能なコードで、本当に読みやすい "クラス名"が必要な場合は、すべてのクラスに "メタクラス"を書くことができます。

template<typename T> class MetaClass{}; 
class Foobar { 
//... 
}; 
template<> class MetaClass<Foobar> { 
public: 
    static std::string className() { 
     return "Foobar"; 
    } 
}; 
std::map<std::string, int> someMap; 
someMap[MetaClass<Foobar>::className()] = 0xff; 
//... 

テンプレートが気に入らない場合は、他の方法で実装することができます(例:仮想メソッド)。

関連する問題