如何获取所有当前栈帧的 f_globals 属性

5 投票
2 回答
3570 浏览
提问于 2025-04-17 11:10

我想获取当前所有的调用栈帧,并检查每个帧的 f_globals 属性。这和 unittest 模块的做法很相似,只不过在我的情况下,并没有抛出异常。traceback.extract_stack() 这个方法无法访问这些信息,但当抛出异常时,sys.exc_info() 中的帧可以获取到。

2 个回答

4
current_frame = sys._getframe(0)

然后你可以使用 f_back 这个属性来向上遍历调用栈(一直到它变成 None 为止)。

需要注意的是,这个功能是特定于 CPython 的,算是一种实现细节。

4

只需使用来自 inspect 模块的 "stack" 函数。

>>> import inspect
>>> inspect.stack()
[(<frame object at 0x02467FE0>, '<stdin>', 1, '<module>', None, None)]

这个函数会返回一个列表,列表中的每个元素都是一个元组,包含了当前运行的框架和关于这个框架的额外信息(具体内容可以参考 Python 文档):

[frame, filename, line number, function name, frame sources, current line index in sources]

如果想查看每个框架对象的 f_globals,可以这样做:

>>> for frame_tuple in inspect.stack():
...    print frame_tuple[0].f_globals.keys()
... 
['frame_tuple', '__builtins__', 'inspect', '__package__', '__name__', 'readline', 'rlcompleter', '__doc__']

不过,"stack" 函数运行起来比较慢,不适合在实际代码中用来做其他事情,除了设置和调试。如果你需要在运行时检查堆栈,比如获取变量值或其他基于检查的代码,建议使用 inspect.currentframe() 来获取当前框架,并通过每个框架的 .f_back 属性来链接到前一个框架,这样会快很多。

你不应该使用 sys._getframe,因为它名字前面的下划线表示这个函数不应该被公开使用。

撰写回答