检查类属性:方法,属性或不存在

时间:2017-10-08 10:48:08

标签: python oop methods attributes

我希望班级检查是否:

  1. 存在所需属性
  2. 如果是方法,则应返回方法
  3. 的结果
  4. 如果是属性,则返回值
  5. 如果不存在,则引发AttributeException
  6. 我的解决方案(不工作):

    class A:
       def __getattr__(self, item):
           try:
               return self.item()
           except AttributeError:
               try:
                   return self.item
               except AttributeError:
                   raise AttributeError
    
       y = 2
       def x(self):
         return 1
    

    我的测试:

    a = A()
    print(a.x)
    

    我的结果:

    <bound method A.x of <__main__.A object at 0x7f992de18c50>>
    

    如您所见,它返回对函数的引用,而不是结果。我哪里做错了?

    解决

    使用

    解决了我的问题
    @property 
    

    装饰器。 我只想要 - 将方法称为属性

2 个答案:

答案 0 :(得分:0)

这是Python的工作方式。方法只是类型绑定方法的属性。

你可以让这项工作更好,但只能启发式。例如。如果你想禁止绑定方法,请检查类型,然后调用。

然而,如果返回该绑定方法,这将意味着您遇到麻烦,因为它应该是属性提供的回调。

如果存在给定名称的属性声明等,您还可以检查对象的 - 属性。

总而言之,我会质疑你的做法。有一个简单的解决方案:让用户做出决定,而不是假设是什么。

答案 1 :(得分:0)

仅当常规查找未找到项目时才会调用

__getattr__。查找项目时,首先运行对象的__getattribute__。如果它引发AttributeError(它没有在对象的dict中找到它) - 那么它会调用__getattr__

您的代码返回bound method的原因是从未执行__getattribute__代码,因为该属性是通过常规查找过程找到的。即使它被执行了,它也行不通。 item是一个包含参数的变量。 self.item不存在;这样做的方法是使用attr = getattr(self, item)

您需要的是@property,它允许您访问类似属性的方法:

    ... class code ...

    @property
    def x(self):
        return 1

a = A()
print a.x
1

请注意,您不能再将该属性作为函数调用:

a.x()
Traceback (most recent call last):
  File "C:\Python27\tests\test.py", line 12, in <module>
    print a.x()
TypeError: 'int' object is not callable