diff --git a/pep-0435.txt b/pep-0435.txt index 6ca2c0b8a..d108ca2e7 100644 --- a/pep-0435.txt +++ b/pep-0435.txt @@ -34,9 +34,25 @@ The idea of adding an enum type to Python is not new - PEP 354 [2]_ is a previous attempt that was rejected in 2005. Recently a new set of discussions was initiated [3]_ on the ``python-ideas`` mailing list. Many new ideas were proposed in several threads; after a lengthy discussion Guido proposed adding -``flufl.enum`` to the standard library [4]_. This PEP is an attempt to -formalize this decision as well as discuss a number of variations that can be -considered for inclusion. +``flufl.enum`` to the standard library [4]_. During the PyCon 2013 language +summit the issue was discussed further. It became clear that many developers +want to see an enum that subclasses ``int``, which can allow us to replace +many integer constants in the standard library by enums with friendly string +representations, without ceding backwards compatibility. An additional +discussion among several interested core developers led to the proposal of +having ``IntEnum`` as a special case of ``Enum``. + +The key dividing issue between ``Enum`` and ``IntEnum`` is whether comparing +to integers is semantically meaningful. For most uses of enumerations, it's +a **feature** to reject comparison to integers; enums that compare to integers +lead, through transitivity, to comparisons between enums of unrelated types, +which isn't desirable in most cases. For some uses, however, greater +interoperatiliby with integers is desired. For instance, this is the case for +replacing existing standard library constants (such as ``socket.AF_INET``) +with enumerations. + +This PEP is an attempt to formalize this decision as well as discuss a number +of variations that were discussed and can be considered for inclusion. Motivation @@ -153,9 +169,9 @@ same named values in the derived class:: >>> Colors.blue is MoreColors.blue True -However, these are not doing comparisons against the integer equivalent -values, because if you define an enumeration with similar item names and -integer values, they will not be identical:: +However, these are not doing comparisons against the integer equivalent values, +because if you define an enumeration with similar item names and integer values, +they will not be identical:: >>> class OtherColors(Enum): ... red = 1 @@ -174,7 +190,7 @@ These enumeration values are not equal, nor do they hash equally:: 2 Ordered comparisons between enumeration values are *not* supported. Enums are -not integers:: +not integers (but see ``IntEnum`` below):: >>> Colors.red < Colors.blue Traceback (most recent call last): @@ -342,6 +358,48 @@ Enumeration values are hashable, so they can be used in dictionaries and sets:: green -> granny smith +IntEnum +------- + +A variation of ``Enum`` is proposed that also subclasses ``int`` - ``IntEnum``. +Such enumerations behave much more similarly to integers. In particular, they +can be compared to integers; by extensions, enumerations of different types can +also be compared to each other:: + + >>> from enum import IntEnum + >>> class Shape(IntEnum): + ... circle = 1 + ... square = 2 + ... + >>> class Request(IntEnum): + ... post = 1 + ... get = 2 + ... + >>> Shape == 1 + False + >>> Shape.circle == 1 + True + >>> Shape.circle == Request.post + True + +However they still can't be compared to ``Enum``:: + + >>> from enum import Enum, IntEnum + >>> class Shape(IntEnum): + ... circle = 1 + ... square = 2 + ... + >>> class Colors(Enum): + ... red = 1 + ... green = 2 + ... + >>> Shape.circle == Colors.red + False + +For the vast majority of code, ``Enum`` is recommended. Only if a greater +degree of interoperatility with integers is required and ``Enum`` does not +fit the bill, ``IntEnum`` should be used. + Pickling --------