Udostępnij za pośrednictwem


Wyliczenia języka C#

Wskazówka

Dopiero zaczynasz programować oprogramowanie? Najpierw zacznij od samouczków Wprowadzenie . Gdy będziesz potrzebował używać wyliczeń do przedstawienia stałego zestawu wyborów w kodzie.

Czy masz doświadczenie w pracy w innym języku? Wyliczenia języka C# działają podobnie do wyliczenia w Java lub C++, z dodatkową obsługą flag bitowych i dopasowywania wzorców. Przejrzyj flagi i sekcje wyrażenia przełącznika pod kątem wzorców specyficznych dla języka C#.

Typ wyliczeniowy (lub enum) definiuje zestaw nazwanych stałych opartych na wartości całkowitej. Użyj wyliczenia, gdy wartość musi być jedną z wartości spośród stałego zestawu opcji, takich jak dni tygodnia, kody stanu HTTP, poziomy dziennika lub kierunki. Wyliczenia sprawiają, że kod jest bardziej czytelny i mniej podatny na błędy niż nieprzetworzone stałe całkowite, ponieważ kompilator wymusza nazwane wartości.

Deklarowanie wyliczenia

Zdefiniuj wyliczenie ze enum słowem kluczowym, po którym następuje nazwa typu i jego składowe:

enum Season
{
    Spring,
    Summer,
    Autumn,
    Winter
}

Domyślnie podstawowy typ to int, a wartości zaczynają się od 0 i zwiększają się o jeden. Season.Spring jest 0, Season.Summer jest 1, i tak dalej.

Określanie bazowego typu i jawnych wartości

Możesz wybrać inny typ całkowity i przypisać jawne wartości, aby kontrolować reprezentację liczbową:

enum HttpStatus : ushort
{
    OK = 200,
    NotFound = 404,
    InternalServerError = 500
}

Użyj jawnych wartości, gdy liczby mają znaczenie zewnętrzne, takie jak kody stanu HTTP lub identyfikatory protokołu. Typ bazowy może być dowolnym typem całkowitym z wyjątkiem char. Użyj byte, , short, ushort, intuint, , longlub ulong.

Używaj enumów w wyrażeniach switch

Wyliczenia działają naturalnie z wyrażeniami switch i dopasowaniem wzorca. Kompilator ostrzeże cię, jeśli nie obsłużysz wszystkich członków, co pomoże zapobiec błędom przy dodawaniu nowej wartości później.

static string DescribeSeason(Season season) => season switch
{
    Season.Spring => "Flowers bloom and temperatures rise.",
    Season.Summer => "Long days and warm weather.",
    Season.Autumn => "Leaves change color and fall.",
    Season.Winter => "Short days and cold temperatures.",
    _ => throw new ArgumentOutOfRangeException(nameof(season))
};
var today = Season.Autumn;
Console.WriteLine(DescribeSeason(today));

Wzorzec odrzucenia (_) obsługuje dowolną wartość, która nie jest jawnie wymieniona. Ponieważ typ bazowy wyliczenia to liczba całkowita, zmienna może przechowywać wartość, która nie odpowiada żadnej nazwanej składowej. Na przykład (Season)99 jest prawidłowy w czasie wykonywania. Wzorzec odrzucenia gwarantuje, że wyrażenie przełącznika bezpiecznie obsługuje te nieoczekiwane wartości. Dopasowywanie wzorca to funkcja języka C#, która testuje wartość względem kształtu lub warunku. W tym przykładzie każdy case sprawdza, czy typ wyliczeniowy jest zgodny z określonym elementem. Wyrażenia switch są jedną z kilku form dopasowywania wzorców. Aby uzyskać więcej informacji na temat dopasowywania wzorców, zobacz Dopasowywanie wzorca.

Flagi bitowe

Gdy wyliczenie reprezentuje kombinację wyborów, a nie pojedynczy wybór, zdefiniuj każdy element członkowski jako potęgę dwóch i zastosuj element FlagsAttribute:

[Flags]
enum FileAccess
{
    None = 0,
    Read = 1,
    Write = 2,
    Execute = 4,
    ReadWrite = Read | Write,
    All = Read | Write | Execute
}

Połącz wartości przy użyciu operatora | i przetestuj poszczególne flagi przy użyciu operatora HasFlag.

var permissions = FileAccess.Read | FileAccess.Write;

Console.WriteLine(permissions);                          // ReadWrite
Console.WriteLine(permissions.HasFlag(FileAccess.Read)); // True
Console.WriteLine(permissions.HasFlag(FileAccess.Execute)); // False

Atrybut [Flags] ma również wpływ na ToString()element . Wyświetla połączone wartości jako nazwy rozdzielane przecinkami (na przykład Read, Write) zamiast liczby pierwotnej. Aby uzyskać więcej informacji, zobacz System.FlagsAttribute.

Konwersja między wyliczeniami a liczbami całkowitymi

Explicitne wyrażenia rzutowania konwertują między typem wyliczeniowym a jego podstawowym typem całkowitym. Jawne rzutowanie używa składni (Type)value, aby zasygnalizować kompilatorowi, że zamierzasz dokonać konwersji.

var status = HttpStatus.NotFound;
ushort code = (ushort)status;
Console.WriteLine($"Status: {status} ({code})"); // Status: NotFound (404)

var fromCode = (HttpStatus)200;
Console.WriteLine(fromCode); // OK

Należy pamiętać, że rzutowanie liczby całkowitej na typ wyliczeniowy nie sprawdza, czy wartość jest zgodna ze zdefiniowanym elementem. Użyj Enum.IsDefined, aby sprawdzić poprawność danych wejściowych liczbowych otrzymywanych ze źródeł zewnętrznych.

Analizowanie ciągów i iterowanie wartości

Klasa podstawowa Enum udostępnia metody analizowania ciągów i iterowania wszystkich zdefiniowanych wartości:

// Parse a string to an enum value:
var parsed = Enum.Parse<Season>("Winter");
Console.WriteLine(parsed); // Winter

// Try to parse safely. It returns false only when the input can't be parsed. Call Enum.IsDefined to validate named members:
if (Enum.TryParse<Season>("Monsoon", out var unknown))
{
    Console.WriteLine(unknown);
}
else
{
    Console.WriteLine("'Monsoon' is not a valid Season"); // 'Monsoon' is not a valid Season
}

// Iterate over all values in an enum:
foreach (var season in Enum.GetValues<Season>())
{
    Console.WriteLine($"{season} = {(int)season}");
}
// Spring = 0
// Summer = 1
// Autumn = 2
// Winter = 3

Użyj Enum.TryParse<TEnum>(String, Boolean, TEnum) zamiast Enum.Parse<TEnum>(String) wtedy, gdy dane wejściowe mogą być nieprawidłowe. Zwraca false zamiast zgłaszać błąd.

Zobacz także