如何检查python类是否有特定的方法?

时间:2014-08-13 20:16:59

标签: python function class methods

class C(Test):
    def __init__(self):
        print "in C init"
        super(C, self).__init__()

    def setup(self):
        print "\tin C setup"

    def runtest(self):
        print "\t\tin C runtest"

    def teardown(self):
        print "\t\t\tin C teardown"

我在不同的模块中有这样的课程。例如,课程ABC等。在一个模块中,我只考虑具有设置和拆卸方法的课程。假设类A没有设置方法,我不想在我的程序的其他部分考虑它,我将构建具有setup和runtest模块的类列表。我可以使用任何python函数吗?处理这个问题的正确方法是什么?

3 个答案:

答案 0 :(得分:3)

我认为这是abstract base class的情况。

class Test(metaclass=ABCMeta):
    @abstractmethod
    def setup(self):
        ...

    @abstractmethod
    def teardown(self):
        ...

    @classmethod
    def __subclasshook__(cls, C):
        if cls is Test:
            if (any("setup" in B.__dict__ for B in C.__mro__) and 
               any("teardown" in B.__dict__ for B in C.__mro___)):
                return True
        return NotImplemented

这定义了类型Test__subclasshook__函数,用于检查类是否定义setup()teardown()。这意味着任何此类都将被视为Test的子类 - issubclass()True返回issubclass(C, Test)

当然,您可以使用与__subclasshook__函数相同的方法手动进行检查,但抽象基类提供了一种很好的(和标准的)方法来定义您想要实现的契约。

答案 1 :(得分:2)

您可以在类本身上使用hasattrcallable(类是对象),例如

if hasattr( C, 'setup' ) and callable( C.setup ):
      classes_with_setup.append(C)

或者,就列表理解而言

classes_with_setup=[ U for U in [A,B,C...] if hasattr(U,'setup') and callable(U.setup)]

设置包含这些功能的类列表。

此方法确实检测到继承:

In [1]: class A(object):
   ...:     def f(self):
   ...:         print 'hi'
   ...:         

In [2]: class B(A):
   ...:     pass
   ...: 

In [3]: hasattr(A,'f')
Out[3]: True

In [4]: hasattr(B,'f')
Out[4]: True

In [5]: hasattr(B,'f') and callable(B.f)
Out[5]: True

答案 2 :(得分:0)

您可以使用getattrcallable方法

setup_method = getattr(your_object, "setup_method", None)
if callable(setup_method):
    setup_method(self.path.parent_op)

首先检查对象是否具有名为" setup_method"的属性。然后检查它该属性是一个方法,然后调用它。