In an Enum
, the members are also Enum
s themselves. The example from the documentation uses the __new__
method of the members to assign a value. You can't use that method, because the new member does not know how it is called within its owning class. Rather, use the initializer. Here's an example:
>>> class AutoNameValueEnum(enum.Enum):
... def __init__(self):
... self._value_ = self._name_.lower()
...
>>> class Color(AutoNameValueEnum):
... RED = ()
...
>>> Color.RED
<Color.RED: 'red'>
Update:
Note that with this solution, value lookups are no longer possible. This is because the enum metaclass stores values before calling the initializer. This will effectively cut you out from pickling your enum and might also break things in some other places. An alternative (which breaks equivalence to similar strings, i.e. a is "foo"
, for values, but nothing else) is to use an unhashable type for the values. The enum class will then do a linear search rather than try to lookup keys for values through a map.
class UnhashableString(str):
def __hash__(self):
raise TypeError
class AutoNameValueEnum(enum.Enum):
def __init__(self):
self._value_ = UnhashableString(self._name_.lower())
class Color(AutoNameValueEnum):
RED = ()
Is the updated example for this alternative. All in all, I think that using the functional interface suggested here is the cleanest solution, because you can be sure that nothing breaks when you use it.