运行此文件foo.py
import inspect
class Parent(object):
def source1(self):
class A(object):
def foo(self):
pass
print inspect.getsource(A)
def source2(self):
class A(object):
def bar(self, a, b, c):
pass
print inspect.getsource(A)
parent = Parent()
parent.source1()
parent.source2()
生成此输出:
class A(object):
def foo(self):
pass
class A(object):
def foo(self):
pass
当我希望它产生这个输出时:
class A(object):
def foo(self):
pass
class A(object):
def bar(self, a, b, c):
pass
我在测试中遇到了这个问题。我在测试方法的主体中重用名称A
和B
作为类名。我正在测试一个依赖于inspect.getsource
的函数,而且......它不起作用,因为后来的测试是从前面提到的A
和{{1}开始的。 } class。
答案 0 :(得分:1)
inspect.getsource调用实际上解析了源文件,查找了类定义,并返回了它在缩进的最低级别找到的第一个它正在寻找的名称。换句话说,它不会做你要求它做的事情。
这是一种略有不同的方法,可以产生您正在寻找的输出,并且可能会满足您的需求:
import inspect
class Parent(object):
def source1(self):
class A1(object):
def foo(self):
pass
A = A1
print inspect.getsource(A)
def source2(self):
class A2(object):
def bar(self, a, b, c):
pass
A = A2
print inspect.getsource(A)
parent = Parent()
parent.source1()
parent.source2()
类定义仍然可以通过您想要的名称引用(例如" A"),但源代码中的实际定义使用不同的名称,因此getsource可以找到它。
答案 1 :(得分:1)
这是因为inspect.getsource
在源文件中找到第一个匹配的class A
。根据Python 2.7.6的545 line
中的inspect.py
,此模式用于查找源。
pat = re.compile(r'^(\s*)class\s*' + name + r'\b')
因此,如果您首先在代码前面定义class A
为
import inspect
class A(object):
pass
class Parent(object):
def source1(self):
class A(object):
def foo(self):
pass
print 'id of A in source1 :', id(A)
print inspect.getsource(A)
def source2(self):
class A(object):
def bar(self, a, b, c):
pass
print 'id of A in source2 :', id(A)
print inspect.getsource(A)
print 'id of A in global :', id(A)
parent = Parent()
parent.source1()
parent.source2()
结果将是
id of A in global : 12512848
id of A in source1 : 12415088
class A(object):
pass
id of A in source2 : 12356672
class A(object):
pass
即使他们的对象id
不同。