Подробное использование типа перечисления Python Enum

Python

В реальной разработке мы не можем обойтись без определения различных типов, когда нам нужно определить типы, мы обычно определяем их через набор целых чисел. Например: определить разные месяцы

JAN 1
FEB 2
MAR 3
...
NOV 11
DEC 12

Большинство людей думают о следующих способах определения:

1. Напрямую использовать метод определения переменных

jan = 1
feb = 2

2. Используйте словарь

d = {"jan": 1, "feb": 2}

3. Используйте переменные класса

class TypeMonth:
    jan = 1
    feb = 2

Для чисел или других типов, представляющих месяцы, после определения никаких изменений не требуется! Однако определенные выше методы могут легко изменить значение типа, например:

d['jan'] = 3

TypeMonth.jan = 3

Это не является ни строгим, ни безопасным в реальной разработке, и нежелательно. При этом вышеперечисленные методы будут иметь разные типы ключей и одинаковое значение.

d = {"jan": 1, "feb": 2, "mar": 2}

Для этого случая после Python 3.4 нам добавили класс перечисления Тип перечисления можно рассматривать как метку или набор констант, обычно используемых для представления каких-то конкретных ограниченных наборов, таких как недели, месяц, статус и т.д. .

перечисляемый класс

Простой пример:

from enum import Enum

class Color(Enum):
    RED = 1
    GREEN = 2
    BLUE = 3

print(Color.RED)
输出结果: Color.RED

Приведенный выше код создает базовый пример перечисления, который, в отличие от нашего обычного класса, расширяет класс Enum. При использовании класса для одновременного получения свойства на выходе отображается не его значение, а элемент перечисления. Это делает код более читаемым.

По сравнению с обычными классами имеет следующие преимущества: ####Не допускается прямое изменение значения элементов перечисления вне класса.

Мы можем попробовать изменить значение тега в перечислении,

Color.RED = 4

После запуска он сообщит об ошибке,

Нет элемента перечисления (переменной класса) с таким же ключом

Также не допускается иметь одно и то же значение ключа в классе перечисления, например, следующий код имеет два одинаковых RED.

class Color(Enum):
    RED = 1
    RED = 1
    GREEN = 2
    BLUE = 3

После запуска выдает ошибку типа.

Перечисления могут иметь одинаковое значение, но каждый ключ с одинаковым значением будет использоваться как псевдоним.

В классе перечисления может быть одно и то же значение, но последующие элементы перечисления являются псевдонимами первого.


class Color(Enum):
    RED = 1
    GREEN = 1
    BLUE = 3

print(Color.GREEN)

输出结果:Color.RED

Как видно из результатов, вывод имеет тип Color.RED, а не Color.GREEN. Если вы не хотите иметь одно и то же значение в классе перечисления, Enum также предоставляет соответствующий метод обработки.

from enum import Enum
from enum import unique

@unique
class Color(Enum):
    RED = 1
    GREEN = 1
    BLUE = 3

print(Color.GREEN)

После запуска код предложит ValueError

Основные операции перечисления

Получить значение метки перечисления

Color.GREEN.value

Получить имя тега перечисления

Color.GREEN.name

перебрать перечисление

for v in Color:
    print(v)

输出结果:
Color.RED
Color.GREEN
Color.BLUE

Перебирать классы перечисления с одинаковым значением

class Color(Enum):
    RED = 1
    GREEN = 2
    BLUE = 3
    BLACK = 1

for v in Color:
    print(v)

输出结果:
Color.RED
Color.GREEN
Color.BLUE

Как видите, имена тегов с одинаковым значением не выводятся. Если вы хотите вывести, используйте следующий метод для обхода

for k, v in Color.__members__.items():
    print(k, v)

输出结果:
RED Color.RED
GREEN Color.GREEN
BLUE Color.BLUE
BLACK Color.RED

Операции сравнения перечисления

Сравнение эквивалентности между перечислениями

result = Color.RED == Color.GREEN
print(result)

输出结果: False

Также поддерживает сравнение идентичности

result = Color.RED is Color.BLACK
print(result)

输出结果: True

Поскольку значения КРАСНОГО и ЧЕРНОГО равны

Сравнение размеров между перечислениями не поддерживается.

Сравнение '>' или '

result = Color.RED > Color.BLACK

преобразование типа enum

Самым большим преимуществом перечисления является то, что оно повышает читабельность нашего кода.

if a ==1:
  pass
elif a == 2:
  pass

Приведенный выше код не очень удобочитаем, потому что мы не знаем, что представляют собой 1 и 2. Но если есть класс перечисления, он другой.

if a == Color.RED.value:
    pass
elif a == Color.GREEN.value:
    pass

По сравнению с первым кодом следующий код намного читабельнее. Так что, если мы преобразуем значение перечисления в имя перечисления? Например, a = 1, вы можете напрямую передать переменную в класс перечисления

a = 1
print(Color(a))

输出结果:
Color.RED

Суммировать

1. Классы перечисления нельзя использовать для создания экземпляров объектов.

2. Чтобы получить доступ к элементу в классе перечисления, непосредственно используйте имя класса для доступа к элементу, к которому необходимо получить доступ, например, цвет.КРАСНЫЙ

3. Ключ = значение, определенное в классе перечисления, значение значения не может быть изменено вне класса.

4. Элементы перечисления можно использовать для сравнения, используя == или

5. Ключи в классе перечисления не могут быть одинаковыми, и Значения могут быть одинаковыми, но каждый Ключ с одним и тем же Значением будет использоваться как псевдоним

6. Классы перечисления можно пройти с помощью for,members.items() может проходить классы с псевдонимами

7. Если значение в классе перечисления не может быть одинаковым, вам нужно импортировать уникальное, чтобы украсить класс перечисления