2017-11-14 6 views
3

キーがintで値が与えられた引数の文字列表記であるマップを初期化するためにC++ 11で導入されたVariadicテンプレート引数を使用できると思います。私はこのテンプレートC++ 11バリデーションテンプレートを使ってEnum To String Mapを初期化する

template<typename... Ts> auto enumList(Ts... args){ 
    QList<int> res = {args...}; 
    return res; 
} 

auto enums = enumList<int, int>(Enums::Enum1, Enums::Enum2); 

Iを経由して列挙int型の表現のリストを初期化することができ

auto map = EnumStringMap<EnumType::Type1, EnumType::Type2>(); 

:私は単にこのような文字列表現に列挙名からマップを作成することができ、その可能であれば

STRINGFY Cマクロで式の文字列表現を得ることができると考えてください

#define STRINGIFY(x) #x 
#define TOSTRING(x) STRINGIFY(x) 

しかし、私は文字列表現に型名や型の値を変換する方法を見つけることができないので、それはまったく可能ですか? 私の目標は、コンパイル時に列挙の文字列表現を保持するマップを生成することです。

QOPで使用されているMOCのようなアプローチは、私にとっては適切ではありません。なぜなら、QObjectに重くてコピーできない列挙型を囲む必要があるからです。

+0

AFAIK C++では不可能です。 C#で可能ですが。私は単純にそのようなマッピング(静的) 'EnumStringMap 'を作成します。 – vahancho

+1

[BETTER_ENUMS](https://github.com/aantron/better-enums)のようなライブラリでよく使われる方法は、マクロを使って列挙型を定義することです。 (それが反映されるまで)。 – Jarod42

+0

@vahanchoは多数の列挙型(おそらく500+)を手動で維持するのが非常に難しい –

答えて

3

マクロは、C++コンパイルの前にプリプロセッサによって処理されます。したがって、関数内でマクロを使用して、enum値のC++名を取得することはできません。

ほとんどのソリューションは、列挙型が定義された時点で使用されるマクロに基づいています。そこに多くは、インターネット上で利用可能な実装があり、それは一般的にそのような何かを:

#define MY_ENUM(a, b, c) enum a {b , c} \ 
Map<a, string> mymap = {{b, STRINGIFY(b)}, {b, STRINGIFY(b)}}; 

MY_ENUM(Color, Red, Blue) 
MY_ENUM(Align, Left, Right) 

別のアプローチは、より多くのコードを生成するために、C++のコードを処理すること、メタコンパイラを使用しています。これは、QtはそのMOCで何をするかで、あなたはQtのにあなたの質問をタグ付けするので、それは

class FooBar : public QObject { 
    Q_OBJECT 
public: 
    enum Action { Open, Save, New, Copy, Cut, Paste, Undo, Redo, Delete }; 
    Q_ENUM(Action) // Not Q_ENUMS !!! 

    static QString convert(Action a) { 
    auto metaEnum = QMetaEnum::fromType<Action>(); 
    return metaEnum.valueToKey(a); 
    } 
}; 

この

は列挙型でなければなりませんという事実のように、いくつかの制約があります..あなたのために行くための最良の方法かもしれません QObject(または Q_GADGET)に定義されている。 Qt documentationで詳しく調べることができます。どのように行われたのかは Woboq articleです。

+0

ありがとう、私はQtによって使用されるアプローチを認識していることを忘れていますが、列挙型は望ましくないQObject –

+0

マクロベースのソリューションは柔軟性がなく、C++の高度なコンパイル時の機能では使用できません。11 –

+1

@ e.jahandar QObjectよりも重さは軽いが、どちらも完璧ではないQ_GADGETを使用できます。完全なC++サポートのためには、C++ 2xを待つ必要があります。あなたが興味があるなら、CppCon2017でハーブ・サッターの話を見てください –

関連する問題