如果你的python脚本执行很慢,有很多种方法对它的性能进行分析,比如cProfile就很好。
如果你想对正在运行的python进程进行性能分析,cProfile则无能为力,因为程序已经在运行,如果是生产环境,不可能为了配合你分析性能而重新启动程序。
Py-spy可以对正在运行的python进程进行分析,其原理是获取调用堆栈,在linux系统下,通过process_vm_readv,在mac下使用vm_read,在windows上使用ReadProcessMemory。
使用一段计算pi的程序来测试py-spy工具的使用,先安装
pip install py-spy
计算pi的程序如下
from __future__ import division
def get_pi(number):
number1 = number+10
b = 10**number1
x1 = b*4//5
x2 = b// -239
he = x1+x2
number *= 2
for i in range(3, number,2):
x1 //= -25
x2 //= -57121
x = (x1+x2) // i
he += x
pai = he*4
pai //= 10**10
paistring=str(pai)
result = paistring[0]+str('.')+paistring[1:len(paistring)]
print(result)
get_pi(1000000)
这段程序会运行一定时间,在运行期间,使用py-spy分析代码
通过获取调用堆栈,可以了解程序内部的执行情况,了解函数之间的调用关系
[root@pyhost ~]# py-spy dump --pid 21512
Process 21512: python test.py
Python v2.7.5 (/usr/bin/python2.7)
Thread 21512 (idle)
get_pi (test.py:15)
<module> (test.py:25)
top 命令可以展示哪些函数被调用执行的次数最多,由于我测试的程序只有一个函数,因此只显示了一个函数。
从显示内容看,13,14,15这3行代码最耗费性能。
[root@pyhost ~]# py-spy top --pid 22135
Collecting samples from 'python test.py' (python v2.7.5)
Total Samples 800
GIL: 100.00%, Active: 100.00%, Threads: 1
%Own %Total OwnTime TotalTime Function (filename:line)
36.00% 36.00% 3.06s 3.06s get_pi (test.py:15)
18.00% 18.00% 2.38s 2.38s get_pi (test.py:14)
40.00% 40.00% 2.32s 2.32s get_pi (test.py:13)
6.00% 6.00% 0.240s 0.240s get_pi (test.py:16)
0.00% 100.00% 0.000s 8.00s <module> (test.py:25)
火焰图可以更加形象直观的展示进程内资源耗费情况
py-spy record -o profile.svg --pid 21512
生成的profile.svg文件可以在浏览器里查看,效果如下
也可以直观的反应出13,14,15 这三行代码比较耗时。
QQ交流群: 211426309