我正在编写一些代码来确定分配给对象的名称。这是用于一般调试工作并进一步熟悉 python 内部结构。
我将其结构化为类装饰器,以便如果可能的话,该类的所有实例都将记录其名称。代码相当长,所以除非被问到,否则我不会发布它。一般技术如下
用代码装饰类的
__init__
方法来做我想做的事设置
caller = inspect.currentframe().f_back
并打开inspect.getframeinfo(caller).filename
并将其发送到ast.parse
. 我在这里不做任何错误检查,因为(1)这只是为了调试/分析/黑客(2)这个确切的过程“刚刚”完成,或者代码不会运行。这有问题吗?找到
ast.Assignment
导致当前正在执行的__init__
方法运行的实例如果
len(assignment.targets) == 1
那么左侧只有一个项目,我可以从targets[0].id
. 在一个简单的形式a = Foo()
中,那么assignment.value
是 的一个实例ast.Call
。如果它是文字(例如列表),那么value
将是该列表并保释,因为我感兴趣的对象没有被分配给名称。
确认这assignment.value.func
实际上type(obj).__call__
是我感兴趣的对象的最佳方法是什么。我很确定我可以保证它“在某处”或者代码甚至不会运行。我只需要它处于最高水平。显而易见的事情是遍历它并确保它不包含任何内部调用。然后我保证我有这个名字。(我的推理是正确的,我不确定它的假设是否正确)。这并不理想,因为如果我对 感兴趣Foo
,这可能会导致我放弃,a = Foo(Bar())
因为我不知道它是否是a = Bar(Foo())
。
当然我可以检查assignment.value.func.id
但是有人可能已经做了Foobar = Foo
什么所以我不想过分依赖这个
任何帮助将不胜感激。与往常一样,我对我可能忽略的任何其他建议或问题感兴趣。
此外,我真的很惊讶我只需要发明“python-internals”标签。