Numpy 用IPython进行性能分析

在IPython中,既可以用timeit分析一小段代码的性能,也可以在运行脚本的时候对整个脚本进行分析。对这两种性能分析方式,我们都将予以介绍。

具体步骤

首先,我们要测量一个代码片段的执行时间。

  1. 测量代码片段的执行时间。

以pylab模式启动IPython。

ipython -pylab

创建一个包含1000个整数的数组,其取值范围在0到1000之间。

In [1]: a = arange(1000)

测量在该数组中查找“任何事情的答案”——42所需要的时间。没错,42是“任何事情的答案”。如果你对此心存疑问,请浏览http://en.wikipedia.org/wiki/42_%28number%29。

In [2]: %timeit searchsorted(a, 42)
100000 loops, best of 3: 7.58 us per loop

  1. 分析一个脚本的性能。

我们将分析一个小脚本的性能。该脚本对一系列不同大小的、包含随机数的矩阵求逆。NumPy数组的.I属性(注意是大写的I)表示数组的逆矩阵。

import numpy

def invert(n):
    a = numpy.matrix(numpy.random.
        rand(n, n))
    return a.I

sizes = 2 ** numpy.arange(0, 12)

for n in sizes:
    invert(n)

可以用如下方式,对该脚本的运行时间进行测量。

In [1]: %run -t invert_matrix.py

IPython CPU timings (estimated):
    User :         6.08 s.
    System :       0.52 s.
    Wall time:      19.26 s.

可以使用p选项对脚本进行性能分析。

In [2]: %run -p invert_matrix.py

852 function calls in 6.597 CPU seconds

    Ordered by: internal time

    ncalls tottime percall cumtime percall filename:lineno(function)
        12   3.228   0.269   3.228     0.2 {numpy.linalg.lapack_lite.dgesv}
        24   2.967   0.124   2.967   0.124 {numpy.core.multiarray._fastCopyAndTranspose}
        12   0.156   0.013   0.156   0.013 {method 'rand' of 'mtrand.RandomState' objects}
        12   0.087   0.007   0.087   0.007 {method 'copy' of 'numpy.ndarray' objects}
        12   0.069   0.006   0.069   0.006 {method 'astype' of 'numpy.ndarray' objects}
        12   0.025   0.002   6.304   0.525 linalg.py:404(inv)
        12   0.024   0.002   6.328   0.527 defmatrix.py:808(getI)
        1   0.017   0.017   6.596   6.596 invert_matrix.py:1()
        24   0.014   0.001   0.014   0.001 {numpy.core.multiarray.zeros}
        12   0.009   0.001   6.580   0.548 invert_matrix.py:3(invert)
        12   0.000   0.000   6.264   0.522 linalg.py:244(solve)
        12   0.000   0.000   0.014   0.001 numeric.py:1875(identity)
        1   0.000   0.000   6.597   6.597 {execfile}
        36   0.000   0.000   0.000   0.000 defmatrix.py:279(__array_finalize__)
        12   0.000   0.000   2.967   0.247 linalg.py:139(_fastCopyAndTranspose)
        24   0.000   0.000   0.087   0.004 defmatrix.py:233(__new__)
        12   0.000   0.000   0.000   0.000 linalg.py:99(_commonType)
        24   0.000   0.000   0.000   0.000 {method '__array_prepare__' of 'numpy.ndarray' objects}
        36   0.000   0.000   0.000   0.000 linalg.py:66(_makearray)
        36   0.000   0.000   0.000   0.000 {numpy.core.multiarray.array}
        12   0.000   0.000   0.000   0.000 {method 'view' of 'numpy.ndarray' objects}
        12   0.000   0.000   0.000   0.000 linalg.py:127(_to_native_byte_order)
        1   0.000   0.000   6.597   6.597 interactiveshell.py:2270(safe_execfile)

攻略小结

我们用性能分析工具对上述NumPy脚本的运行过程进行了分析。下表对分析工具的输出项目进行了总结。

描述
ncalls 调用次数
tottime 总的函数执行时间
percall 单次调用的执行时间,即tottime/ncalls
cumtime 函数的累计执行时间,包括该函数本身的执行时间、在该函数内部调用其他函数花费的时间和递归调用花费的时间

Python教程

Java教程

Web教程

数据库教程

图形图像教程

大数据教程

开发工具教程

计算机教程