元组的实例在枚举类中没有成员(pylint没有成员)

Smu*_*ule 8 python enums pylint python-3.x

从枚举类使用成员“值”和“等于”时,我从pylint收到以下错误:“代码”:“无成员”“消息”:““元组”的实例没有“值”成员”版本:pylint 2.3.1 astroid 2.2.5 Python 3.6.3

The code is executed as expected. I am just wondering if there might be something I am doing wrong (I am not a pro python programmer), or if there is a more "pythonic" way to achieve the same result:

from enum import Enum

class DefaultEnum(Enum):

    def __new__(self,val,_name,_type):
        obj = object.__new__(self)
        obj._value_ = val
        obj._publicName = _name
        obj._type = _type
        return obj

    def __str__(self):
        return self._publicName

    def equals(self,_string):
        return _string == str(self)

class GlobalEnum(DefaultEnum):
    TRUE = 0,'True',str()
    FALSE = 1,'False',str()


GlobalEnum.TRUE.value
>> 0
GlobalEnum.TRUE.equals('True')
>> True
repr(GlobalEnum.TRUE)
>> <GlobalEnum.TRUE: 0>
Run Code Online (Sandbox Code Playgroud)

I am currently using the "# pylint: disable=no-member" comment to disable the warning, but I would prefer not to do this... The same goes for white-listing the class as I still would like pylint to report other findings.

小智 8

要回答您的主要问题:

  1. pylint 无法识别动态创建的属性,并且
  2. Enum许多方面都是“特殊的” ,其中之一是Enum的成员实际上是enum该类的实例:
    from enum import Enum

    class MyEnum(Enum):
        val1 = 0

    print(type(MyEnum.val1)) # <enum 'MyEnum'>


    class MyClass:
        val1 = 0

    print(type(MyClass.val1)) # <class 'int'>
Run Code Online (Sandbox Code Playgroud)

也就是说,当您TRUEGlobalEnum类中进行设置时,Python 会将其转换TRUE为的实例GlobalEnum,但是pylint不理解这一点,并且由于看起来像是为其GlobalEnum.TRUE分配了元组值,因此pylint认为这是一个元组,没有“值”会员。

要回答是否有更“ pythonic”的方式来实现相同的结果,我不确定您要完成什么,但是看起来您在做一些奇怪的事情。例如:

  1. __new__()传递了一个作为它的第一个参数,但是您将其称为“自我”,按照(近)通用惯例,它指的是一个实例,这会使阅读起来非常混乱。通常人们会称之为cls

  2. 按照惯例_name,单个前导下划线(“ ”,“ _type”)通常用于表示“私有”成员,因此,大多数读者会在函数签名中使用它们,这会造成混淆。如果要使用保留字作为参数名称,通常的约定是使用结尾的下划线(例如“ type_”,“ exec_”)。

  3. 我不知道你想什么你的“完成_type”属性,但现在两者GlobalEnum.TRUEGlobalEnum.FALSE会返回一个空字符串作为他们的_type,因为str()返回一个字符串实例,并没有ARGS字符串将是空的。如果希望它返回str 类型,则应将其设置为str(不带括号)。

  4. 认为您想要做的是创建一个枚举,与您在定义中指定的int或字符串相比,该枚举的值将为True。在这种情况下,equals()您可以覆盖内置的__eq__()magic方法,而不是使用用户定义的方法(您几乎肯定会在某个时候忘记使用该方法),以便可以改用通常的==运算符:

from enum import Enum


class BaseEnum(Enum):

    def __init__(self, int_value, str_value):
        self._value_ = int_value
        self.str_value = str_value

    def __eq__(self, other):
        return other == self.value or other == self.str_value


class MyEnum(BaseEnum):
    TRUE = 0, 'True'
    FALSE = 1, 'False'


print(MyEnum.TRUE == 0)  # True
print(MyEnum.TRUE == 'True')  # True
a = MyEnum.TRUE
print(a == MyEnum.TRUE) # True

print(MyEnum.TRUE.value)  # 0
print(MyEnum.TRUE.str_value)  # 'True'
Run Code Online (Sandbox Code Playgroud)

[请注意,str_value上面只是一个常规类属性,意味着可以设置它。要使其为只读,可以使用不带setter 的属性装饰器。]