为了补充这里的答案,在 Python 3 中最好的方法是这样的:
import inspect
class Test:
@staticmethod
def test(): pass
isstatic = isinstance(inspect.getattr_static(Test, "test"), staticmethod)
我们使用getattr_static 而不是getattr,因为getattr 将检索绑定的方法或函数,而不是staticmethod 类对象。您可以对classmethod 类型和property 进行类似的检查(例如,使用@property 装饰器定义的属性)
请注意,即使它是staticmethod,也不要假设它是在类中定义的。方法源可能源自另一个类。要获得真正的来源,您可以查看底层函数的限定名称和模块。例如:
class A:
@staticmethod:
def test(): pass
class B: pass
B.test = inspect.getattr_static(A, "test")
print("true source: ", B.test.__qualname__)
从技术上讲,任何方法都可以用作“静态”方法,只要它们是在类本身上调用的,所以请记住这一点。例如,这将完全正常:
class Test:
def test():
print("works!")
Test.test()
该示例不适用于Test 的实例,因为该方法将绑定到该实例并改为以Test.test(self) 调用。
在某些情况下,实例和类方法也可以用作静态方法,只要第一个参数处理得当。
class Test:
def test(self):
print("works!")
Test.test(None)
也许另一个罕见的情况是staticmethod,它也绑定到一个类或实例。例如:
class Test:
@classmethod
def test(cls): pass
Test.static_test = staticmethod(Test.test)
虽然从技术上讲它是staticmethod,但它的行为确实像classmethod。所以在你的反省中,你可能会考虑检查__self__(在__func__上递归),看看该方法是否绑定到一个类或实例。