我正在尝试编写一个文档测试工具,用于检查文档字符串是否与实际的函数签名(以及其他内容)匹配。但是,我遇到了一些障碍。我无法找到一种方法来确定给定的函数是否属于某个类。
import inspect
def func1():
pass
class Foo:
def method(self):
pass
print(inspect.ismethod(func1)) # prints False
print(inspect.ismethod(Foo().method)) # prints True
print(inspect.ismethod(Foo.method)) # prints False - I want something that prints True here
问题是方法通常以self
作为第一个参数,并且从未记录过(出于显而易见的原因)。这会导致我的测试失败,因为他们会遇到一个没有记录的参数。
我宁愿不显式检查第一个参数是否被调用self
并跳过它,因为a)没有什么能阻止函数有一个名为self
的参数和b)名称{{1本身是一个约定问题(因此你可以使用一个名为self
的第一个参数的方法,在任何一种情况下我的工具都会失败。我也不能只是初始化一个对象并检查该函数是否是一个方法,因为这会在任何具有this_is_definitely_not_self
中所需参数的类时失败。
所以问题是,在实际绑定到对象之前,有什么方法可以检测函数是否为方法?或者我是否需要让自己只是检查第一个参数是否被调用__init__
?
答案 0 :(得分:1)
一个选项是__qualname__
。对于方法,这包括您可以使用的类名。这是添加内容的原因之一:
类,函数,方法,描述符或生成器实例的限定名称。
有关此属性的详情,请参阅PEP 3155's proposal。
当然,由于在类定义期间设置了__qualname__
,因此当函数动态添加到类时,可能会出现误报。所以,这个答案基本上涵盖了一个函数是否已在类中定义的问题。
所以,没有明确的方法来检测这个,因为在类中定义并通过类访问的函数和类外的函数没有区别。 (大多数情况下除__qualname__
外)。
明智的做法是使用__qualname__
作为"快速"检查是否已在类中定义了函数,如果是False
,则返回使用inspect.signature
function和self
检查'self' in signature(func).parameters
。
你无法覆盖所有案例,这是Python,我几乎可以做任何我喜欢的事情。据称,我们都同意成年人的意见。 :)