当前位置:首页>python>Python学习--枚举类的使用

Python学习--枚举类的使用

  • 2026-09-26 09:15:10
Python学习--枚举类的使用

1. 基本使用

定义和访问

from enum import Enum, IntEnum, Flag, auto# 基础枚举class Color(Enum):    RED = 1    GREEN = 2    BLUE = 3class Priority(IntEnum):    LOW = 1    MEDIUM = 2    HIGH = 3# 访问方式print(Color.RED)           # Color.REDprint(Color.RED.name)      # 'RED'print(Color.RED.value)     # 1# 通过值获取枚举print(Color(1))            # Color.REDprint(Color['RED'])        # Color.RED

2. 遍历枚举

class Status(Enum):    PENDING = 'pending'    RUNNING = 'running'    COMPLETED = 'completed'    FAILED = 'failed'# 遍历所有成员for status in Status:    print(f"{status.name}: {status.value}")# 输出:# PENDING: pending# RUNNING: running# COMPLETED: completed# FAILED: failed# 获取所有成员列表members = list(Status)print(members)  # [<Status.PENDING: 'pending'>, ...]# 获取所有名称names = [member.name for member in Status]print(names)  # ['PENDING', 'RUNNING', 'COMPLETED', 'FAILED']# 获取所有值values = [member.value for member in Status]print(values)  # ['pending', 'running', 'completed', 'failed']

3. 比较操作

class Day(Enum):    MON = 'Monday'    TUE = 'Tuesday'    WED = 'Wednesday'# 身份比较day1 = Day.MONday2 = Day.MONday3 = Day.TUEprint(day1 is day2)           # Trueprint(day1 is Day.MON)        # Trueprint(day1 is not day3)       # True# 值比较print(day1 == Day.MON)        # Trueprint(day1 == day3)           # Falseprint(day1 != Day.TUE)        # True# 不支持大小比较(除非是 IntEnum)class Level(IntEnum):    LOW = 1    MEDIUM = 2    HIGH = 3print(Level.LOW < Level.HIGH)  # True (仅 IntEnum 支持)

4. 在函数和方法中使用

from enum import Enumfrom typing import Listclass UserRole(Enum):    ADMIN = 'admin'    EDITOR = 'editor'    VIEWER = 'viewer'    GUEST = 'guest'class User:    def __init__(self, name: str, role: UserRole):        self.name = name        self.role = role    def has_permission(self, required_roles: List[UserRole]) -> bool:        """检查用户是否有权限"""        return self.role in required_roles    def upgrade_role(self, new_role: UserRole):        """升级用户角色"""        if new_role not in UserRole:            raise ValueError(f"Invalid role: {new_role}")        self.role = new_role# 使用user = User("Alice", UserRole.VIEWER)print(user.has_permission([UserRole.ADMIN, UserRole.EDITOR]))  # Falseprint(user.has_permission([UserRole.VIEWER, UserRole.GUEST]))  # True

5. 在数据验证中使用

from enum import Enumfrom pydantic import BaseModel, validatorclass ProductCategory(Enum):    ELECTRONICS = 'electronics'    CLOTHING = 'clothing'    BOOKS = 'books'    FOOD = 'food'class Product(BaseModel):    name: str    price: float    category: ProductCategory    @validator('category')    def validate_category(cls, v):        if v not in ProductCategory:            raise ValueError(f'Invalid category. Must be one of: {[c.value for c in ProductCategory]}')        return v# 使用try:    product = Product(        name="Laptop",        price=999.99,        category=ProductCategory.ELECTRONICS    )    print(product.category.value)  # 'electronics'except ValueError as e:    print(f"Error: {e}")

6. 模式匹配(Python 3.10+)

from enum import Enumclass HTTPStatus(Enum):    OK = 200    CREATED = 201    BAD_REQUEST = 400    NOT_FOUND = 404    INTERNAL_ERROR = 500def handle_response(status: HTTPStatus):    match status:        case HTTPStatus.OK | HTTPStatus.CREATED:            return "Success"        case HTTPStatus.BAD_REQUEST:            return "Client error"        case HTTPStatus.NOT_FOUND:            return "Resource not found"        case HTTPStatus.INTERNAL_ERROR:            return "Server error"        case _:            return "Unknown status"# 使用print(handle_response(HTTPStatus.OK))       # "Success"print(handle_response(HTTPStatus.NOT_FOUND)) # "Resource not found"

7. 结合字典使用

from enum import Enumclass ErrorCode(Enum):    VALIDATION_ERROR = 1001    AUTH_ERROR = 1002    NOT_FOUND = 1003# 错误信息映射ERROR_MESSAGES = {    ErrorCode.VALIDATION_ERROR: "输入数据验证失败",    ErrorCode.AUTH_ERROR: "认证失败,请重新登录",    ErrorCode.NOT_FOUND: "请求的资源不存在"}# 配置映射CONFIG = {    ErrorCode.VALIDATION_ERROR: {"retry": False, "log_level": "warning"},    ErrorCode.AUTH_ERROR: {"retry": True, "log_level": "error"},}def handle_error(error: ErrorCode):    message = ERROR_MESSAGES.get(error, "未知错误")    config = CONFIG.get(error, {})    print(f"Error {error.value}: {message}")    print(f"Config: {config}")

8. 序列化和反序列化

import jsonfrom enum import Enumfrom typing import Anyfrom dataclasses import dataclass, asdictclass OrderStatus(Enum):    PENDING = "pending"    PROCESSING = "processing"    SHIPPED = "shipped"    DELIVERED = "delivered"@dataclassclass Order:    id: int    customer: str    status: OrderStatus    def to_dict(self) -> dict:        return {            'id': self.id,            'customer': self.customer,            'status': self.status.value  # 使用 .value 序列化        }    @classmethod    def from_dict(cls, data: dict) -> 'Order':        return cls(            id=data['id'],            customer=data['customer'],            status=OrderStatus(data['status'])  # 从值反序列化        )# 使用order = Order(1, "Alice", OrderStatus.PENDING)# 序列化为 JSONorder_dict = order.to_dict()json_str = json.dumps(order_dict)print(json_str)  # {"id": 1, "customer": "Alice", "status": "pending"}# 反序列化data = json.loads(json_str)restored_order = Order.from_dict(data)print(restored_order.status)  # OrderStatus.PENDING

9. Flag 枚举的位运算

from enum import Flag, autoclass Permission(Flag):    NONE = 0    READ = auto()    # 1    WRITE = auto()   # 2    EXECUTE = auto() # 4    ALL = READ | WRITE | EXECUTE  # 7class User:    def __init__(self, name: str, permissions: Permission):        self.name = name        self.permissions = permissions    def has_permission(self, permission: Permission) -> bool:        return permission in self.permissions    def add_permission(self, permission: Permission):        self.permissions |= permission    def remove_permission(self, permission: Permission):        self.permissions &= ~permission# 使用user = User("Bob", Permission.READ | Permission.WRITE)print(user.has_permission(Permission.READ))   # Trueprint(user.has_permission(Permission.EXECUTE)) # Falseuser.add_permission(Permission.EXECUTE)print(user.permissions)  # Permission.READ|WRITE|EXECUTEuser.remove_permission(Permission.WRITE)print(user.permissions)  # Permission.READ|EXECUTE

10. 实用工具函数

from enum import Enumfrom typing import Optional, Listclass TrafficLight(Enum):    RED = 'stop'    YELLOW = 'caution'    GREEN = 'go'# 检查枚举值是否存在def is_valid_light(color: str) -> bool:    try:        TrafficLight(color)        return True    except ValueError:        return False# 获取枚举描述def get_light_description(color: TrafficLight) -> str:    descriptions = {        TrafficLight.RED: "完全停止",        TrafficLight.YELLOW: "准备停止",        TrafficLight.GREEN: "可以通行"    }    return descriptions.get(color, "未知")# 枚举转换工具class EnumUtils:    @staticmethod    def get_enum_by_value(enum_class, value):        """通过值获取枚举实例"""        try:            return enum_class(value)        except ValueError:            return None    @staticmethod    def get_values(enum_class) -> List:        """获取所有枚举值"""        return [member.value for member in enum_class]    @staticmethod    def get_names(enum_class) -> List[str]:        """获取所有枚举名称"""        return [member.name for member in enum_class]# 使用print(is_valid_light('stop'))  # Trueprint(get_light_description(TrafficLight.RED))  # "完全停止"light = EnumUtils.get_enum_by_value(TrafficLight, 'go')print(light)  # TrafficLight.GREEN

最佳实践建议

  1. 使用有意义的名称:枚举成员名称应该清晰表达其含义

  2. 值保持稳定:枚举值一旦确定不应轻易改变

  3. 类型提示:使用枚举作为类型提示可以提高代码可读性

  4. 适当文档:为复杂的枚举添加文档字符串

  5. 考虑序列化:如果需要序列化,确保值是可序列化的类型

最新文章

随机文章