ホームページ >バックエンド開発 >C++ >if/switch ステートメントを使用せずに C 列挙値をテキストとして出力する方法は?

if/switch ステートメントを使用せずに C 列挙値をテキストとして出力する方法は?

Patricia Arquette
Patricia Arquetteオリジナル
2024-11-29 22:55:12610ブラウズ

How to Print C   Enum Values as Text Without Using if/switch Statements?

if/switch を使用せずに C で列挙値をテキストとして出力する

C では、列挙型は名前付き定数のセットを表す便利な方法を提供します。ただし、列挙値を出力するときのデフォルトの動作は、その数値表現を表示することです。

次のような列挙型があるとします。

enum Errors {
    ErrorA = 0,
    ErrorB,
    ErrorC,
};

次を使用して列挙値を出力しようとすると、 std::cout:

Errors anError = ErrorA;
std::cout << anError; // 0 will be printed

テキスト表現の代わりに数値 0 を取得します。 「エラーA」。この問題は、std::cout に列挙型を文字列に変換するためのサポートが組み込まれていないために発生します。

解決策

1。マップの使用

1 つの方法は、各列挙値をテキスト表現に関連付けるマップを作成することです。

#include <map>
#include <string_view>

std::ostream& operator<<(std::ostream& out, const Errors value) {
    static const auto strings = [] {
        std::map<Errors, std::string_view> result;
        #define INSERT_ELEMENT(p) result.emplace(p, #p);
        INSERT_ELEMENT(ErrorA);     
        INSERT_ELEMENT(ErrorB);     
        INSERT_ELEMENT(ErrorC);             
        #undef INSERT_ELEMENT
        return result;
    };

    return out << strings[value];
}

2.線形検索で構造体の配列を使用する

もう 1 つのオプションは、それぞれ列挙値とそのテキスト表現を含む構造体の配列を使用して、線形検索を実行することです。

#include <string_view>

std::ostream& operator<<(std::ostream& out, const Errors value) {
#define MAPENTRY(p) {p, #p}
    const struct MapEntry {
        Errors value;
        std::string_view str;
    } entries[] = {
        MAPENTRY(ErrorA),
        MAPENTRY(ErrorB),
        MAPENTRY(ErrorC),
        {ErrorA, 0} //doesn't matter what is used instead of ErrorA here...
    };
#undef MAPENTRY
    const char* s = 0;
    for (const MapEntry* i = entries; i->str; i++) {
        if (i->value == value) {
            s = i->str;
            break;
        }
    }

    return out << s;
}

3. switch/case の使用

最後に、switch/case ステートメントも使用できます:

#include <string>

std::ostream& operator<<(std::ostream& out, const Errors value) {
    return out << [value] {
    #define PROCESS_VAL(p) case(p): return #p;
        switch(value) {
            PROCESS_VAL(ErrorA);     
            PROCESS_VAL(ErrorB);     
            PROCESS_VAL(ErrorC);
        }
    #undef PROCESS_VAL
    };
}

ソリューションのテスト:

これらのソリューションをテストするには、次のコマンドを使用して実行可能ファイルを作成します。コード:

#include <iostream>

int main(int argc, char** argv) {
    std::cout << ErrorA << std::endl << ErrorB << std::endl << ErrorC << std::endl;
    return 0;   
}

この実行可能ファイルを実行すると、列挙値のテキスト表現が出力されます:

ErrorA
ErrorB
ErrorC

以上がif/switch ステートメントを使用せずに C 列挙値をテキストとして出力する方法は?の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。