【问题标题】:Link ATLAS/MKL to an installed Numpy将 ATLAS/MKL 链接到已安装的 Numpy
【发布时间】:2014-03-07 10:05:12
【问题描述】:

TL;DR如何在不重建的情况下将 ATLAS/MKL 链接到现有 Numpy。

我使用 Numpy 计算大矩阵,发现它非常慢,因为 Numpy 只使用 1 个核心进行计算。经过大量搜索后,我发现我的 Numpy 没有链接到像 ATLAS/MKL 这样的优化库。这是我的 numpy 配置:

>>>import numpy as np
>>>np.__config__.show()
blas_info:
    libraries = ['blas']
    library_dirs = ['/usr/lib']
    language = f77
lapack_info:
    libraries = ['lapack']
    library_dirs = ['/usr/lib']
    language = f77
atlas_threads_info:
    NOT AVAILABLE
blas_opt_info:
    libraries = ['blas']
    library_dirs = ['/usr/lib']
    language = f77
    define_macros = [('NO_ATLAS_INFO', 1)]
atlas_blas_threads_info:
  NOT AVAILABLE
openblas_info:
  NOT AVAILABLE
lapack_opt_info:
    libraries = ['lapack', 'blas']
    library_dirs = ['/usr/lib']
    language = f77
    define_macros = [('NO_ATLAS_INFO', 1)]
atlas_info:
  NOT AVAILABLE
lapack_mkl_info:
  NOT AVAILABLE
blas_mkl_info:
  NOT AVAILABLE
atlas_blas_info:
  NOT AVAILABLE
mkl_info:
  NOT AVAILABLE

出于这个原因,我想将 ATLAS/MKL 链接到 Numpy。但是,我的 Numpy 是从 PIP 安装的,所以我不想手动安装,因为我想使用最新版本。我已经进行了一些搜索,但它们仅用于从头开始构建。因此,我的问题是:

  • 有没有办法将 ATLAS/MKL 链接到 Numpy 而无需再次重建?
  • 我发现配置信息保存在 Numpy 安装文件夹的 _config_.py 中。那么修改它会解决我的问题吗?如果是,请告诉我怎么做?

【问题讨论】:

    标签: python performance numpy linear-algebra blas


    【解决方案1】:

    假设您正在运行某种风格的 linux,以下是您可以做到的一种方法:

    1. 找出当前使用ldd链接的BLAS库numpy。

      • 对于 v1.10 之前的 numpy 版本:

        $ ldd /<path_to_site-packages>/numpy/core/_dotblas.so
        

        例如,如果我通过apt-get 安装 numpy,它会链接到

        ...
        libblas.so.3 => /usr/lib/libblas.so.3 (0x00007fed81de8000)
        ...
        

        如果_dotblas.so 不存在,这可能意味着 numpy 在最初安装时未能检测到任何 BLAS 库,在这种情况下,它根本不会构建任何 BLAS-依赖的组件。如果您使用 pip 安装 numpy 而不手动指定 BLAS 库(见下文),通常会发生这种情况。如果您想链接到外部 BLAS 库,恐怕您别无选择,只能重建 numpy。


      • 对于 numpy v1.10 及更新版本:

        _dotblas.so has been removed 来自最新版本的 numpy,但您应该能够检查 multiarray.so 的依赖关系:

        $ ldd /<path_to_site-packages>/numpy/core/multiarray.so
        
    2. 如果您还没有安装 ATLAS/MKL/OpenBLAS。顺便说一句,我绝对会推荐 OpenBLAS 而不是 ATLAS - 看看 this answer(尽管基准测试数据现在可能有点过时了)。

    3. 使用 update-alternatives 创建指向您选择的新 BLAS 库的符号链接。例如,如果您将libopenblas.so 安装到/opt/OpenBLAS/lib,您会这样做:

      $ sudo update-alternatives --install /usr/lib/libblas.so.3 \
                                           libblas.so.3 \
                                           /opt/OpenBLAS/lib/libopenblas.so \
                                           50
      

      您可以为单个目标库配置多个符号链接,允许您在多个已安装的 BLAS 库之间手动切换。

      例如,当我调用 $ sudo update-alternatives --config libblas.so.3 时,我可以在 3 个库中进行选择:

        Selection    Path                                    Priority   Status
      ------------------------------------------------------------
        0            /opt/OpenBLAS/lib/libopenblas.so         40        auto mode
        1            /opt/OpenBLAS/lib/libopenblas.so         40        manual mode
        2            /usr/lib/atlas-base/atlas/libblas.so.3   35        manual mode
      * 3            /usr/lib/libblas/libblas.so.3            10        manual mode
      

    如果你真的想要“最新”版本的 numpy,你也可以看看my answer on compiling numpy from source with OpenBLAS integration

    使用 pip 安装支持 BLAS 的 numpy

    ​​>

    正如 @tndoan 在 cmets 中提到的那样,可以通过将配置文件放在 ~/.numpy-site.cfg 中来使 pip 尊重 numpy 的特定配置 - 有关详细信息,请参阅 this answer

    我个人的偏好是手动配置和构建 numpy。这不是特别困难,它可以让你更好地控制 numpy 的配置。

    【讨论】:

    • 感谢您的帮助。转到numpy.__path__ 中的文件夹core 后,我找不到_dotblas.so。我使用 PIP 安装了 Numpy,所以它在其他文件夹中吗?
    • 你的答案和what I found in Internet一样。我将尝试手动构建它。感谢您的支持。
    • 对于仍然想使用 pip 和配置文件重新安装的人,here 是他们的解决方案。 @ali_m:请您编辑您的帖子以将此链接放入您的答案中。谢谢
    • 关于使用 openBlas 的建议,我在 scipy.org/scipylib/building/linux.html 找到了这个。截至 2014 年 1 月,ATLAS 是推荐使用的库,因为当与多处理模块(或任何使用 os.fork)结合使用时,OpenBLAS 会死锁,而旧版本(
    • @LGenzelis 我相信该问题已在 2014 年 2 月 19 日的this PR 中得到解决(也请参阅here 的讨论)。就在几天前,我构建了最新版本的 numpy (v1.11.0) 和 OpenBLAS (v0.2.17),并且我一直在使用 multiprocessing 的代码中毫无问题地使用它们。不幸的是,numpy 文档的部分内容很久没有更新了。
    【解决方案2】:

    答案取决于 NumPy 最初是如何构建的。如果它是针对 BLAS 和 LAPACK 构建的,那么至少没有办法强制 numpy.dot 稍后在不重建的情况下使用 ATLAS/MKL。其他函数不使用numpy.dot,您可以使用update-alternatives 更改符号链接libblas.so.3liblapack.so.3 的目标。这是因为numpy.dot 需要 ATLAS 样式的 CBLAS 或 OpenBLAS/MKL,但不需要来自 netlib 的 BLAS/CBLAS 和 LAPACK。

    我正在使用 openSUSE,并且我已经从 netlib 安装了标准的 cblas-devel。然而,强制 NumPy 使用随附的 cblas/cblas-devel 似乎是不可能的。也就是说,如果您针对 netlib BLAS/LAPACK/CBLAS(作为官方包)构建 NumPy,则无法构建 _dotblas.so(提供 numpy.dot 的 BLAS 版本)(1.10 之前),或者 multiarray.so(1.10和更高版本)根本不链接到libblas.so.3。请参阅 github 上的问题:https://github.com/numpy/numpy/issues/1265 和引用的 Debian 错误报告:https://bugs.debian.org/cgi-bin/bugreport.cgi?bug=464784。也许有人可以深入研究源代码来制作补丁......无论如何,它只是一个受到影响的功能(numpy.dot),您现在可以随时使用更快的 OpenBLAS 轻松重建整个 NumPy,所以之后可能没什么大不了的全部。

    结论:您可以稍后链接到 ATLAS/MKL/OpenBLAS 而无需重建,但如果 NumPy 最初不是针对 ATLAS/MKL/OpenBLAS 构建的,numpy.dot 仍然会非常慢(因为 @987654335 @ 根本就没有使用 any BLAS,一旦编译完成,你就无能为力了)。

    更新:实际上你可以强制 numpy 构建_dotblas.so。我已经为 numpy-1.9.2 做了一个补丁:

    diff -Npru numpy-1.9.2.orig/numpy/core/setup.py numpy-1.9.2/numpy/core/setup.py
    --- numpy-1.9.2.orig/numpy/core/setup.py        2015-02-01 11:38:25.000000000 -0500
    +++ numpy-1.9.2/numpy/core/setup.py     2016-03-28 01:31:12.948885383 -0400
    @@ -953,8 +953,8 @@ def configuration(parent_package='',top_
         #blas_info = {}
         def get_dotblas_sources(ext, build_dir):
             if blas_info:
    -            if ('NO_ATLAS_INFO', 1) in blas_info.get('define_macros', []):
    -                return None # dotblas needs ATLAS, Fortran compiled blas will not be sufficient.
    +            #if ('NO_ATLAS_INFO', 1) in blas_info.get('define_macros', []):
    +            #    return None # dotblas needs ATLAS, Fortran compiled blas will not be sufficient.
                 return ext.depends[:3]
             return None # no extension module will be built
    

    现在_dotblas.so 已链接到libblas.so.3,您可以使用update-alternatives 来测试差异。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2018-01-27
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-12-23
      • 1970-01-01
      相关资源
      最近更新 更多