在Python中添加并初始化枚举类变量

2024-04-25 21:56:39 发布

您现在位置:Python中文网/ 问答频道 /正文

我正在实现一个enumclass,并希望检索有关enum成员的聚合信息。每个enum代表一个具有不同管脚数的转接板,我想得到所有板上的最大管脚数。我的方法是在每个成员的__init__期间添加一个类属性\u max\u pins。你知道吗

问题是,如果成员也将成为成员,则不可能提前定义\u max\u pins。在成员之后定义它是没有帮助的,因为这样成员就不能在__init__期间访问它 我已经看过Declare a static variable in an enum class,但是表可以在__init__之后设置—这是可能的,但是需要在初始化之后再次扫描所有成员。你知道吗

class IgelTyp(Enum):
    LED_1 = (24, 1)
    LED_2 = (24, 2)
    LED_3 = (16, 4)

    _max_pin = -1

    def __init__(self, pins, groups):
        if _max_pin < pins//groups:     # gives error
            _max_pin = pins//groups

    @classmethod
    def get_max_pins(cls):
        return cls._max_pin

上面的代码生成UnboundLocalError: local variable '_max_pin' referenced before assignment

当我在成员定义前面移动{max\u pin赋值时,它告诉我TypeError: __init__() missing 2 required positional arguments: ...

编辑1 实际上,TypeError不管我将赋值放在类中的什么位置都会被引发。 当我使用IgelTyp._max_pin = -1时,我得到一个NameError: name 'IgelTyp' is not defined

有没有人有一个高效且可读的解决方案?你知道吗


Tags: led定义initdefpin成员enumvariable
1条回答
网友
1楼 · 发布于 2024-04-25 21:56:39

一次性解决方案:

__init__更改为直接访问类的字典:

def __init__(self, pins, groups):
    max_pin = self.__class__.__dict__.get('max_pin', 0)
    self.__class__.max_pin = max(max_pin, pins//groups)

有趣的是,通过在__init__末尾添加这一行,您可以很容易地让每个LED成员存储自己的max_pin

    self.max_pin = pins//groups

所以:

>>> IgelTyp.max_pin
24

但是:

>>> IgelType.LED_2.max_pin
12


可重复使用的解决方案

创建自己的类属性描述符,并使用它来阻止max_pin成为IgelTyp成员:

class ClassVar:              # add (object) if using Python 2
    "a class variable"

    def __init__(self, value):
        # store initial value
        self.value = value

    def __get__(self, *args):
        # get value in ClassVar instance (only doable because all instances
        # share same value)
        return self.value

    def __set__(self, _, value):
        # save value in ClassVar instance (only doable because all instances
        # share same value)
        self.value = value

描述符,如property通常将值存储在实例本身上,以便每个实例都有自己的值(例如示例中的24、12和4);但是,由于您希望知道所有实例中的最大管脚数,因此我们只需将单个值保存在ClassVar实例上。你知道吗

IgelTyp的更改:

class IgelTyp(Enum):

    LED_1 = (24, 1)
    LED_2 = (24, 2)
    LED_3 = (16, 4)

    max_pin = ClassVar(0)

    def __init__(self, pins, groups):
        self.max_pin = max(self.max_pin, pins//groups)

使用中:

>>> IgelTyp.max_pin
24
>>> IgelTyp.LED_2.max_pin
24

相关问题 更多 >