Python enumeration (Enum) usage tutorial
enumerate(Enum) is the built-in standard library of Python 3.4+, which is specially used to define named constants with clear semantics, unmodifiable, and limited values.
And the traditional way of expressing constants by capitalizing variables (such asMONTH_JAN = 1), enumerations can provide:
- Static Safety: Avoid typing wrong variable names or passing in illegal values;
- Clear Semantics: Enhance code readability;
- Normalized access and traversal: unified access through member names or values, and supports traversal of all members;
- Business logic cohesion: Constant-related logic can be directly encapsulated in enumeration classes.
In production-level code, proper use of enumerations can significantly improve the robustness and maintainability of the code.
1. Basic enumeration definition
Python provides two ways to create enumerations: quick factory functions, and more flexible custom subclasses.
Method 1: Quickly create factory functions
Suitable for applications that require only a set of sequentially increasing default values (from1start) scene:
The enumeration members generated in this way have two fixed properties:
name:String name of the member, for exampleMonth.Jan.namefor'Jan'value: The automatically assigned value of the member, e.g.Month.Jan.valuefor1
Applicable scenarios: Simple, temporary constant grouping, no custom values or additional methods required.
Method 2: Customized enumeration class (recommended for production)
inheritEnumBase classes can define more flexible and readable enumerations, while strengthening constraints through decorators and custom behaviors.
**@uniqueFunction: **
In regular development, this decorator should always be added to enumeration classes to prevent inadvertent duplication of values, which may lead to logical confusion.
2. Access methods of enumeration members
Enumeration members cannot be used directly==Compares to integer strings (unless usingIntEnumand other special subcategories), it is recommended to use the following four normalization methods:
Tip: Use it directly
Weekday(1)When obtaining enumeration members, if the incoming value is invalid, an exception will be thrown immediately. This is safer than using integer comparison and can quickly locate illegal data.
3. Practical advanced features
3.1 Automatic assignment (auto())
You can use it when the enumeration value itself is not important and is just used to distinguish different members.auto()Automatically assign consecutive values (default from1start):
auto()Different default values may be generated in different enumeration base classes (such asIntFlagwill be generated bit by bit), please refer to the official documentation for details.
3.2 Customize member values and bind additional properties/methods
enumeration membersvalueCan be of any type (tuple, list, object, etc.), and enumeration classes can be defined like ordinary classes__init__and instance methods to achieve encapsulation of data and behavior.
Design Idea: Placing business logic closely related to constants (such as calculations and state flow rules) inside the enumeration class can effectively prevent logic from being scattered throughout the code and improve maintainability.
3.3 Traverse all enumeration members
pass__members__Attributes can obtain the mapping from member names to members to facilitate traversal and display:
If used@uniquedecorator,__members__There will be no aliases generated by duplicate values, and the traversal results will be cleaner.
4. Practical application example: gender enumeration
Traditional code may use0/1/2Indicates gender, which is poorly readable and easily mistransmitted. Using enumerations can completely solve this problem:
Summary of advantages:
- Type Safety: Limit parameter types during the value transfer stage to avoid
1andGender.MALEmisuse. - Easy to read and use: in the code
Gender.FEMALECompare1More expressive. - Extensible: When expanding gender categories in the future, you only need to modify the enumeration class, and the caller does not need to look for the meaning of the number everywhere.
5. Convenience subclasses for Python 3.11+
If the enumeration value ** must be a native string or integer ** and needs to be directly compatible with the original type (such asLogLevel.INFO == "info"returnTrue), you can use the new ones added in Python 3.11StrEnum、IntEnum、IntFlagand other subcategories.
NOTE:
StrEnumandIntEnumAlthough it brings the convenience of compatibility, it may also weaken type checking, requiring a trade-off between convenience and security.
6. Summary of best practices
- Always add
@uniqueDecorator Prevent duplicate values from appearing in the same enumeration class and avoid hidden bugs. - Prefer using custom subclasses instead of factory functions The subclass method is easier to expand, document, and can bind business logic.
- Avoid using values directly for equality comparison
Unless using
StrEnum/IntEnum, otherwise the correct way is to use the enumeration members themselves for comparison. - Encapsulate relevant logic into enumeration classes
as before
Planet.surface_gravity, improve cohesion and reduce external logic scatter. - Follow naming conventions
Use camelCase for enumeration class names (such as
Weekday), use all capital letters for member names (e.g.MONDAY), compliant with PEP 8 and community practices.
7. Summary
Python enumerations solve three core pain points in traditional constant definitions:
- Lack of semantic safety: An error is often not reported immediately when a variable name is mistyped or an illegal value is passed in.
- Fuzzy value boundaries: The caller does not know what values the constant can take
- Business logic is scattered: calculations and rules related to constants are scattered in various modules
By introducingEnumand its subclasses, the code can not only achieve stronger security, readability and maintainability, but also naturally bind constant "data" and "behavior" together, in line with the principles of object-oriented design.
Although the functions of Python enumerations are not as rich as those of some statically typed languages (such as Java), they can already meet the vast majority of production scenarios and are a powerful helper for writing high-quality Python code.

