我想获得有关python中特定函数的调用者的信息。例如:
class SomeClass():
def __init__(self, x):
self.x = x
def caller(self):
return special_func(self.x)
def special_func(x):
print "My caller is the 'caller' function in an 'SomeClass' class."
是否可以使用python?
答案 0 :(得分:11)
是的,sys._getframe()
函数允许您从当前执行堆栈中检索帧,然后您可以使用inspect
module中的方法和文档进行检查;您将在f_locals
属性以及f_code
信息中查找特定的本地人:
import sys
def special_func(x):
callingframe = sys._getframe(1)
print 'My caller is the %r function in a %r class' % (
callingframe.f_code.co_name,
callingframe.f_locals['self'].__class__.__name__)
请注意,您需要注意检测每个帧中找到的信息类型。
sys._getframe()
返回一个框架对象,您可以按照每个框架上的f_back
引用链接整个堆栈。或者,您可以使用inspect.stack()
function生成包含其他信息的框架列表。
答案 1 :(得分:3)
一个例子:
def f1(a):
import inspect
print 'I am f1 and was called by', inspect.currentframe().f_back.f_code.co_name
return a
def f2(a):
return f1(a)
将检索“立即”呼叫者。
>>> f2(1)
I am f1 and was called by f2
如果没有从另一个人那里得到你(在IDLE中):
>>> f1(1)
I am f1 and was called by <module>
答案 2 :(得分:2)
感谢Jon Clements的回答,我能够创建一个返回所有呼叫者的有序列表的函数:
def f1():
names = []
frame = inspect.currentframe()
## Keep moving to next outer frame
while True:
try:
frame = frame.f_back
name = frame.f_code.co_name
names.append(name)
except:
break
return names
并在链中调用时:
def f2():
return f1()
def f3():
return f2()
def f4():
return f3()
print f4()
看起来像这样:
['f2', 'f3', 'f4', '<module>']
在我的情况下,我会在'<module>'
及之后过滤掉任何内容,然后将最后一项作为原始来电者的名称。
或者在首次出现以'<'
开头的任何名称时修改原始循环以保释:
frame = frame.f_back
name = frame.f_code.co_name
if name[0] == '<':
break
names.append(name)