Skip to content

Python 工具/实用程序

Python 的生态系统包含各种内置模块和第三方工具,这些工具帮助进行开发、调试和性能分析。以下是标准库中的一些关键示例。

dis 模块帮助你理解 Python 字节码(bytecode),即 CPython 在执行之前将你的源代码编译成的中间表示形式。它对于性能调优或理解 Python 如何执行特定结构非常有用。

你可以从命令行使用 dis(python -m dis your_script.py),也可以在代码中以编程方式使用。dis.dis() 函数接受函数、方法、类或代码对象。

让我们反汇编一个简单的函数:

import dis
def calculate_sum(a, b):
"""Calculates the sum of two numbers."""
result = a + b
print(f"{a} + {b} = {result}")
return result
# Disassemble the function
dis.dis(calculate_sum)

这可能会产生类似以下的输出(字节码在不同 Python 版本之间可能略有差异):

4 0 LOAD_FAST 0 (a)
2 LOAD_FAST 1 (b)
4 BINARY_ADD
6 STORE_FAST 2 (result)
5 8 LOAD_GLOBAL 0 (print)
10 LOAD_FAST 0 (a)
12 FORMAT_VALUE 0
14 LOAD_CONST 1 (' + ')
16 LOAD_FAST 1 (b)
18 FORMAT_VALUE 0
20 LOAD_CONST 2 (' = ')
22 LOAD_FAST 2 (result)
24 FORMAT_VALUE 0
26 BUILD_STRING 5
28 CALL_FUNCTION 1
30 POP_TOP
6 32 LOAD_FAST 2 (result)
34 RETURN_VALUE

pdb 模块为 Python 程序提供了一个交互式源代码调试器(debugger)。它允许你设置断点(breakpoints),逐行单步执行代码,检查变量(variables),并理解程序流程。

你可以从命令行调用 pdb(python -m pdb your_script.py),或者在代码中直接使用 import pdb; pdb.set_trace() 设置断点。从 Python 3.7 开始,内置的 breakpoint() 函数是进入调试器的推荐方式。

考虑这个脚本(sum_debug.py):

def calculate_sum(a, b):
result = a + b
breakpoint() # 在此处进入调试器
print(f"{a} + {b} = {result}")
return result
num1 = 10
num2 = 20
calculate_sum(num1, num2)
print("Finished.")

运行 python sum_debug.py 将在 breakpoint() 行暂停执行,并进入 pdb 交互式会话:

-> print(f"{a} + {b} = {result}")
(Pdb)

然后你可以使用诸如 n(下一行)、c(继续执行)、p <variable>(打印变量值)、l(列出源代码)、q(退出)等命令。输入 help 查看完整的命令列表。

profile 和 cProfile 模块:性能分析

Section titled “profile 和 cProfile 模块:性能分析”

cProfile(因开销较低而推荐使用)和 profile 是标准的 Python 模块,用于性能分析(profiling)。它们通过测量在不同函数中花费的时间来帮助识别代码中的瓶颈(bottlenecks)。

你可以从命令行运行分析器(profiler):python -m cProfile your_script.py

让我们分析一个简单的脚本(profile_example.py):

def slow_function():
total = 0
for i in range(10000):
total += i
return total
def fast_function():
return sum(range(10000))
slow_function()
fast_function()
print("Profiling done.")

运行 python -m cProfile -s cumulative profile_example.py 可能会输出:

Profiling done.
4 function calls in 0.001 CPU seconds
Ordered by: cumulative time
ncalls tottime percall cumtime percall filename:lineno(function)
1 0.000 0.000 0.001 0.001 {built-in method builtins.exec}
1 0.000 0.000 0.001 0.001 profile_example.py:1(<module>)
1 0.001 0.001 0.001 0.001 profile_example.py:1(slow_function)
1 0.000 0.000 0.000 0.000 profile_example.py:7(fast_function)
1 0.000 0.000 0.000 0.000 {built-in method builtins.sum}
1 0.000 0.000 0.000 0.000 {method 'disable' of '_lsprof.Profiler' objects}

输出显示了调用次数(ncalls)、函数本身花费的总时间(tottime)、每次调用的平均时间(percall)、函数及其调用的所有函数花费的累计时间(cumtime)以及函数信息。像 snakeviz 这样的工具可以可视化分析 cProfile 输出文件,提供更好的洞察。

注意:旧教程中提到的 tabnanny 模块已弃用,并在 Python 3 中移除。现代代码质量工具(如 Linter,例如 flake8、pylint)和格式化工具(例如 black)负责处理缩进和代码风格检查。