Automatically setting an enum member's value to its name

后端 未结 2 1436
时光取名叫无心
时光取名叫无心 2020-12-17 09:02

I\'ve been messing around with python\'s enum library and have come across a conundrum. In the docs, they show an example of an auto-numbering enum, wherein something is def

2条回答
  •  情深已故
    2020-12-17 09:43

    Perhaps you are looking for the name attribute which is automatically provided by the Enum class

    >>> class Animal(Enum):
    ...     ant = 1
    ...     bee = 2
    ...     cat = 3
    ...     dog = 4
    ...
    
    >>> Animal.ant.name == "ant"
    True
    

    Though if you really want to shoot yourself in the foot. And I'm sure this will introduce a whole world of gotchas (I've eliminated the most obvious one).

    from enum import Enum, EnumMeta, _EnumDict
    
    class AutoStrEnumDict(_EnumDict):
        def __setitem__(self, key, value):
            super().__setitem__(key, key)
    
    class AutoStrEnumMeta(EnumMeta):
        @classmethod
        def __prepare__(metacls, cls, bases):
            return AutoStrEnumDict()
        def __init__(self, name, bases, attrs):
            super().__init__(name, bases, attrs)
            # override Enum.__str__
            # can't put these on the class directly otherwise EnumMeta overwrites them
            # should also consider resetting __repr__, __format__ and __reduce_ex__
            if self.__str__ is not str.__str__:
                self.__str__ = str.__str__
    
    class AutoStrNameEnum(str, Enum, metaclass=AutoStrEnumMeta):
        pass
    
    class Animal(AutoStrNameEnum):
        horse = ()
        dog = ()
    
    print(Animal.horse)
    assert Animal.horse == "horse"
    assert str(Animal.horse) == "horse" 
    # and not equal to "Animal.horse" (the gotcha mentioned earlier)
    

提交回复
热议问题