Enum to string in C++11

后端 未结 6 1811
囚心锁ツ
囚心锁ツ 2021-02-03 21:52

I realize this has been asked before more than once on SO but I couldn\'t find a question explicitly looking for a current solution to this issue with C++11, so here we go again

6条回答
  •  有刺的猬
    2021-02-03 22:34

    I like a hack using the C preprocessor, which I first saw here: http://blogs.msdn.com/b/vcblog/archive/2008/04/30/enums-macros-unicode-and-token-pasting.aspx .

    It uses the token-pasting operator # .

    // This code defines the enumerated values:
    
    #define MY_ENUM(x) x,
    enum Fruit_Type {
    MY_ENUM(Banana)
    MY_ENUM(Apple)
    MY_ENUM(Orange)
    };
    #undef MY_ENUM
    
    // and this code defines an array of string literals for them:
    
    #define MY_ENUM(x) #x,
            const char* const fruit_name[] = {
    MY_ENUM(Banana)
    MY_ENUM(Apple)
    MY_ENUM(Orange)
            };
    #undef MY_ENUM
    
    // Finally, here is some client code:
    
    std::cout << fruit_name[Banana] << " is enum #" << Banana << "\n";
    
    // In practice, those three "MY_ENUM" macro calls will be inside an #include file.
    

    Frankly, it's ugly and. but you end up typing your enums exactly ONCE in an include file, which is more maintainable.

    BTW, on that MSDN blog link (see above) a user made a comment with a trick that makes the whole thing much prettier, and avoids #includes:

    #define Fruits(FOO) \
    FOO(Apple) \
    FOO(Banana) \
    FOO(Orange)
    
    #define DO_DESCRIPTION(e)  #e,
    #define DO_ENUM(e)  e,
    
    char* FruitDescription[] = {
    Fruits(DO_DESCRIPTION)
    };
    
    enum Fruit_Type {
    Fruits(DO_ENUM)
    };
    
    // Client code:
    
    std::cout << FruitDescription[Banana] << " is enum #" << Banana << "\n";
    

    (I just noticed that 0x17de's answer also uses the token-pasting operator)

提交回复
热议问题