web-dev-qa-db-ja.com

「char」列挙型を使用できない理由

列挙型として「char」を使用できない理由を知りたいのですが。基本的な列挙型として、byte、sbyte、int、uint、long、ulong、short、ushortがあるためです。次に、列挙型のデフォルトの基本タイプは何ですか?

41
Praveen Sharma

デフォルトのタイプはintです。 MSDNのC# reference で詳細をご覧ください。 MSDNで C#言語仕様 へのリンクも見つけることができます。制限の理由は、おそらく言語仕様のセクション4.1.5のこれらのステートメントに由来すると思います。

Char型は整数型として分類されますが、次の2つの点で他の整数型とは異なります。

•他の型からchar型への暗黙的な変換はありません。特に、sbyte、byte、およびushort型には、char型を使用して完全に表現できる値の範囲がありますが、sbyte、byte、またはushortからcharへの暗黙的な変換は存在しません。

•char型の定数は、char型へのキャストと組み合わせて、文字リテラルまたは整数リテラルとして記述する必要があります。たとえば、(char)10は '\ x000A'と同じです。

15
tvanfosson

私はこれが古い質問であることを知っていますが、この情報は私に役立つでしょう:

C#.NET 4.0の列挙型の値の型としてcharを使用しても問題はないようです(おそらく3.5ですが、これはテストしていません)。これが私がやったことであり、それは完全に機能します:

public enum PayCode {
    NotPaid = 'N',
    Paid = 'P'
}

Enumをcharに変換します。

PayCode enumPC = PayCode.NotPaid;
char charPC = (char)enumPC; // charPC == 'N'

文字を列挙型に変換します。

char charPC = 'P';
if (Enum.IsDefined(typeof(PayCode), (int)charPC)) { // check if charPC is a valid value
    PayCode enumPC = (PayCode)charPC; // enumPC == PayCode.Paid
}

チャータイプから期待するのと同じように、魅力のように機能します!

79
kad81

これは私が使用している回避策です

enum MyEnum
{
    AA = 'A',
    BB = 'B',
    CC = 'C'
};

static void Main(string[] args)
{
    MyEnum e = MyEnum.AA;
    char value = (char)e.GetHashCode(); //value = 'A'
}
13
Emir

技術的には、これを行うことはできません。ただし、列挙型をバイトに変換してから、それをcharに変換できます。これは、目標が次のようなものである場合に役立ちます(これを実現することは不可能であることを実現します:

public enum CharEnum
{
    one = '1'
}

ただし、ASCII byte値を使用して、次のように変換することで、これを行うことができます。

public enum CharEnum
{
    one = 49,
    two = 50
}

次に、byteとcharに変換して、char値を取得できます。それは本当にきれいではありませんが、charを取得することが最終的な目標である場合は機能します。 ASCIIの範囲外の文字が必要な場合は、unicodeとint値を使用することもできます。:-)

3

Ecma International のECMA標準335、Common Language Infrastructure(CLI)を参照してください。 CLIでは、基になるタイプをcharまたはboolにすることができますが、C#およびVB.Netでは許可されていません。価値のあることとして、C++/CLIでは、基になる型としてSystem :: Charを使用できます。

C#とVB.Netでは、構文上の理由のみで、基本型としてcharとboolを許可していないと思います。

1
user34660

VB.NETおよびCLIコンシューマーをターゲットにして、次のようにchar enumをコンパイルできます(ILサポート(拡張)が有効になっているVB.NETまたはC#プロジェクトで最も簡単です)。

.class public auto ansi sealed Hafner.Testing.EdgeCase.CharEnum
       extends [mscorlib]System.Enum
{
    .field public specialname rtspecialname char value__
    .field public static literal valuetype Hafner.Testing.EdgeCase.CharEnum Min = char(0)
    .field public static literal valuetype Hafner.Testing.EdgeCase.CharEnum Zero = char(0)
    .field public static literal valuetype Hafner.Testing.EdgeCase.CharEnum Max = char(65535)
    .field public static literal valuetype Hafner.Testing.EdgeCase.CharEnum DuplicateSameValue = char(65) //A
    .field public static literal valuetype Hafner.Testing.EdgeCase.CharEnum duplicateSameValue = char(65) //A
    .field public static literal valuetype Hafner.Testing.EdgeCase.CharEnum DuplicateOtherValue = char(90) //Z
    .field public static literal valuetype Hafner.Testing.EdgeCase.CharEnum duplicateOtherValue = char(88) //X

}
0
Christoph
char charPC = 'P';
if (Enum.IsDefined(typeof(PayCode), (PayCode)charPC)) { 
        // check if charPC is a valid value
        PayCode enumPC = (PayCode)charPC; // enumPC == PayCode.Paid
}
  • 小さな変更を行いました。すべてのケースで、列挙型に依存する場合は、(int)に変換する必要はありません。しかし、それをenum型自体に直接キャストする場合は、常に機能するはずです。
0
Mike