roc*_*ker 9 python benchmarking numpy blas atlas
与链接到OpenBLAS的numpy相比,我试图改变与ATLAS相关联的numpy的性能.我得到了一些我在下面描述的ATLAS的奇怪结果.
用于评估矩阵 - 矩阵乘法(又名sgemm)的Python代码如下所示:
import sys
sys.path.insert(0, "numpy-1.8.1")
import numpy
import timeit
for i in range(100, 501, 100):
setup = "import numpy; m1 = numpy.random.rand(%d, %d).astype(numpy.float32)" % (i, i)
timer = timeit.Timer("numpy.dot(m1, m1)", setup)
times = timer.repeat(100, 1)
print "%3d" % i,
print "%7.4f" % numpy.mean(times),
print "%7.4f" % numpy.min(times),
print "%7.4f" % numpy.max(times)
Run Code Online (Sandbox Code Playgroud)
如果我运行这个脚本与numpy链接到ATLAS我测量的时间会有很大的变化.您可以在frist列中看到矩阵大小,然后通过运行矩阵矩阵乘法100倍获得的执行时间的均值,最小值和最大值:
100 0.0003 0.0003 0.0004
200 0.0023 0.0010 0.0073
300 0.0052 0.0026 0.0178
400 0.0148 0.0066 0.0283
500 0.0295 0.0169 0.0531
Run Code Online (Sandbox Code Playgroud)
如果我使用一个线程将numpy链接到OpenBLAS重复此过程,则运行时间会更稳定:
100 0.0002 0.0002 0.0003
200 0.0014 0.0014 0.0015
300 0.0044 0.0044 0.0047
400 0.0102 0.0101 0.0105
500 0.0169 0.0168 0.0177
Run Code Online (Sandbox Code Playgroud)
任何人都可以解释这个观察吗?
编辑:附加信息:
ATLAS的最小值和最大值不是异常值,时间分布在给定范围内.
我通过https://gist.github.com/uweschmitt/768bd165477d7c14095e上传了i = 500的ATALS次数
给定时间来自不同的运行,因此avg,min和max值略有不同.
编辑:其他发现:
可能是因为CPU限制(http://www.scipy.org/scipylib/building/linux.html#step-1-disable-cpu-throttling)吗?我不太了解CPU throtting以判断它对我的测量的影响.遗憾的是,我无法在目标机器上设置/取消设置它.
我无法重现,但我想我知道原因。我在 Linux 64 机器上使用 Numpy 1.8.1。
首先,我用 ATLAS 得到的结果(我在最后一列中添加了标准差):
100 0.0003 0.0002 0.0025 0.0003
200 0.0012 0.0010 0.0067 0.0006
300 0.0028 0.0026 0.0047 0.0004
400 0.0070 0.0059 0.0089 0.0004
500 0.0122 0.0109 0.0149 0.0009
Run Code Online (Sandbox Code Playgroud)
现在,Anaconda 提供的 MKL 结果:
100 0.0003 0.0001 0.0155 0.0015
200 0.0005 0.0005 0.0006 0.0000
300 0.0018 0.0017 0.0021 0.0001
400 0.0039 0.0038 0.0042 0.0001
500 0.0079 0.0077 0.0084 0.0002
Run Code Online (Sandbox Code Playgroud)
MKL 速度更快,但分布一致。
ATLAS 在编译时进行调整,它将尝试不同的配置和算法,并为您的特定硬件集保持最快。如果您安装预编译版本,则您将使用构建机器的最佳配置,而不是您自己的配置。这种错误配置可能是造成传播的原因。就我而言,ATLAS 是我自己编写的。
相反,OpenBLAS 是针对特定架构进行手动调整的,因此任何二进制安装都是等效的。MKL 动态决定。
如果我在从存储库安装的 Numpy 上运行脚本并与预编译的 ATLAS 链接(SSE3 未激活),就会发生以下情况:
100 0.0007 0.0003 0.0064 0.0007
200 0.0021 0.0015 0.0090 0.0009
300 0.0050 0.0040 0.0114 0.0010
400 0.0113 0.0101 0.0186 0.0011
500 0.0217 0.0192 0.0329 0.0020
Run Code Online (Sandbox Code Playgroud)
这些数字与您的数据更相似。
为了完整起见,我要求一位朋友在她的机器上运行该代码片段,该机器已从 Ubuntu 存储库安装了 numpy,但没有 ATLAS,因此 Numpy 又回到了糟糕的默认设置:
100 0.0007 0.0007 0.0008 0.0000
200 0.0058 0.0053 0.0107 0.0014
300 0.0178 0.0175 0.0188 0.0003
400 0.0418 0.0401 0.0528 0.0014
500 0.0803 0.0797 0.0818 0.0004
Run Code Online (Sandbox Code Playgroud)
那么,可能会发生什么?
您的 ATLAS 安装不是最佳的,这就是您出现这种分散情况的原因。我的数据是在笔记本电脑上的 Intel i5 CPU @ 1.7 GHz 上运行的。我不知道你有哪台机器,但我怀疑它比我的慢几乎三倍。这表明 ATLAS 尚未完全优化。
我怎样才能确定?
运行numpy.show_config()会告诉您它链接到哪些库以及它们在哪里。输出是这样的:
atlas_threads_info:
libraries = ['lapack', 'ptf77blas', 'ptcblas', 'atlas']
library_dirs = ['/usr/lib64/atlas-sse3']
define_macros = [('ATLAS_INFO', '"\\"3.8.4\\""')]
language = f77
include_dirs = ['/usr/include']
blas_opt_info:
Run Code Online (Sandbox Code Playgroud)
如果这是真的,如何解决?
您可能有一个过时的预编译二进制图集(它是某些包的依赖项),或者您用于编译它的标志是错误的。最顺利的解决方案是从源代码构建 RMPS。以下是针对 CentOS 的说明。
请注意,OpenBLAS 尚不兼容multiprocessing,因此请注意其限制。如果你对线性代数非常感兴趣,MKL 是最好的选择,但它很昂贵。学者可以从 Continuum Anaconda Python 发行版免费获取它,许多大学都拥有校园范围的许可证。