深入理解 PYTHON 虚拟机:PYC 文件结构
在本篇文章当中主要给大家介绍一下 .py 文件在被编译之后对应的 pyc 文件结构,pyc 文件当中的一个核心内容就是 python 字节码。
PYC 文件
pyc 文件是 Python 在解释执行源代码时生成的一种字节码文件,它包含了源代码的编译结果和相关的元数据信息,以便于 Python 可以更快地加载和执行代码。
Python 是一种解释型语言,它不像编译型语言那样将源代码直接编译成机器码执行。Python 的解释器会在运行代码之前先将源代码编译成字节码,然后将字节码解释执行。.pyc 文件就是这个过程中生成的字节码文件。
当 Python 解释器首次执行一个 .py 文件时,它会在同一目录下生成一个对应的 .pyc 文件,以便于下次加载该文件时可以更快地执行。如果源文件在修改之后被重新加载,解释器会重新生成 .pyc 文件以更新缓存的字节码。
生成 PYC 文件
正常的 python 文件需要通过编译器变成字节码,然后将字节码交给 python 虚拟机,然后 python 虚拟机会执行字节码。整体流程如下所示:
我们可以直接使用 compile all 模块生成对应文件的 pyc 文件。
➜ pvm ls
demo.py hello.py
➜ pvm python -m compileall .
Listing '.'...
Listing './.idea'...
Listing './.idea/inspectionProfiles'...
Compiling './demo.py'...
Compiling './hello.py'...
➜ pvm ls
__pycache__ demo.py hello.py
➜ pvm ls __pycache__
demo.cpython-310.pyc hello.cpython-310.pyc
复制代码
python -m compileall .
命令将递归扫描当前目录下面的 py 文件,并且生成对应文件的 pyc 文件。
PYC 文件布局
第一部分魔数由两部分组成:
第一部分 魔术是由一个 2 字节的整数和另外两个字符回车换行组成的, "\r\n" 也占用两个字节,一共是四个字节。这个两个字节的整数在不同的 python 版本还不一样,比如说在 python3.5 当中这个值为 3351 等值,在 python3.9 当中这个值为 3420,3421,3422,3423,3424等值(在 python 3.9 的小版本)。
第二部分 Bit Field 这个字段的主要作用是为了将来能够实现复现编译结果,但是在 python3.9a2 时,这个字段的值还全部是 0 。详细内容可以参考