为了账号安全,请及时绑定邮箱和手机立即绑定

为什么反汇编一个Python类定义会显示两个相同的类名的LOAD_CONST?

为什么反汇编一个Python类定义会显示两个相同的类名的LOAD_CONST?

湖上湖 2023-10-18 16:00:55
我想知道为什么PythonLOAD_CONST在定义一个类时会两次使用相同的值(类名)。当我运行这段代码时:from dis import disdis("class A(): pass")这是我得到的输出:  1           0 LOAD_BUILD_CLASS              2 LOAD_CONST               0 (<code object A at 0x0000021DCE681B70, file "<dis>", line 1>)              4 LOAD_CONST               1 ('A')              6 MAKE_FUNCTION            0              8 LOAD_CONST               1 ('A')             10 CALL_FUNCTION            2             12 STORE_NAME               0 (A)             14 LOAD_CONST               2 (None)             16 RETURN_VALUEDisassembly of <code object A at 0x0000021DCE681B70, file "<dis>", line 1>:  1           0 LOAD_NAME                0 (__name__)              2 STORE_NAME               1 (__module__)              4 LOAD_CONST               0 ('A')              6 STORE_NAME               2 (__qualname__)              8 LOAD_CONST               1 (None)             10 RETURN_VALUE正如您在第 3 行和第 5 行中看到的,有两个LOAD_CONST带有类名。LOAD_CONST如果类名已经加载,为什么还要使用相同的数据创建第二个呢?MAKE_FUNCTION这和他们之间有什么关系吗LOAD_CONST?我在 python 3.7.4 64 位上运行它
查看完整描述

1 回答

?
慕姐4208626

TA贡献1852条经验 获得超7个赞

 CPython 中的类型创建暂时使用函数对象作为类主体。第一个“A”用于该函数的名称。第二个“A”用于类名。

帖子的其余部分详细解释了这个反汇编:

 0 LOAD_BUILD_CLASS

builtins.__build_class__入堆栈。随后由 CALL_FUNCTION 调用它来构造一个类。

 2 LOAD_CONST               0 (<code object A at 0xCAFEF00D, file "<dis>", line 1>)

将代码 obj 压入堆栈(这实际上包含解析的类块 - 继续阅读)

 4 LOAD_CONST               1 ('A')

将“A”压入堆栈

 6 MAKE_FUNCTION            0

将新的函数对象压入堆栈。此操作还消耗堆栈上的前两个内容(此函数的代码 obj 及其限定名称)

 8 LOAD_CONST               1 ('A')

再次将“A”压入堆栈,以便可以用作 中的第二个参数builtins.__build_class__,即类名。

10 CALL_FUNCTION            2

使用堆栈中的“A”和一个函数对象,调用__build_class__(<func>, 'A'). 操作名称后面的 2 指的是所咀嚼的位置参数的数量。最右边的位置参数位于堆栈顶部,因此它们将是:类名'A',然后是 MAKE_FUNCTION 中剩余的 obj,它体现了类定义。这些参数的“下面”是可调用的__build_class__,这个操作也消耗它。未提供任何接受的可选参数__build_class__(func, name, /, *bases, [metaclass], **kwds) -> class

12 STORE_NAME               0 (A)

A = <top of stack>,本质上是在命名空间中绑定新创建的类 obj

14 LOAD_CONST               2 (None)

RETURN_VALUE 将返回堆栈顶部,但类语句 exec 不需要返回值,因此None在返回之前加载。

16 RETURN_VALUE

我们完成了。


查看完整回答
反对 回复 2023-10-18
  • 1 回答
  • 0 关注
  • 77 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信