分发使用LAPACK用Cython基于扩展(Distributing Cython based ex

2019-08-16 23:11发布

我正在写一个Python模块,包括用Cython扩展和使用LAPACK (和BLAS )。 我愿意用任何clapacklapacke ,或某种f2cf2py解决方案,如果必要的。 最重要的是,我能够调用lapackblas从用Cython在没有Python的调用开销紧凑循环程序。

我发现一个例子这里 。 然而,这取决于例如SAGE。 我希望我的模块是安装不安装SAGE,因为我的用户不太可能想要或需要SAGE为别的。 我的用户很可能有像numpy的,SciPy的,熊猫包和scikit学会安装,所以这些将是合理的依赖。 什么是接口使用的最佳组合,并且会是什么最小的setup.py文件看起来像,可以获取必要的信息(从numpy的,SciPy的,等等)进行编译?

编辑:这是我落得这样做。 它适用于我的MacBook,但我不知道它是如何携带。 肯定有更好的办法。

from distutils.core import setup
from distutils.extension import Extension
from Cython.Distutils import build_ext
import numpy
from Cython.Build import cythonize
from numpy.distutils.system_info import get_info

# TODO: This cannot be the right way
blas_include = get_info('blas_opt')['extra_compile_args'][1][2:]
includes = [blas_include,numpy.get_include()]

setup(
    cmdclass = {'build_ext': build_ext},
    ext_modules = cythonize([Extension("cylapack", ["cylapack.pyx"],
                                       include_dirs = includes,
                                       libraries=['blas','lapack'])
                   ])
)

这样做是因为,在我的MacBook中, clapack.h头文件在同一目录cblas.h 。 然后我就可以做到这一点,我PYX文件:

ctypedef np.int32_t integer

cdef extern from "cblas.h":
    double cblas_dnrm2(int N,double *X, int incX)
cdef extern from "clapack.h":
    integer dgelsy_(integer *m, integer *n, integer *nrhs, 
    double *a, integer *lda, double *b, integer *ldb, integer *
    jpvt, double *rcond, integer *rank, double *work, integer *
    lwork, integer *info)

Answer 1:

如果我理解正确的问题,你可以做的BLAS和LAPACK例程使用SciPy的的用Cython包装的。 这些包装都记录在这里:

  • BLAS
  • LAPACK

作为文档状态,你是负责检查你传递给这些功能的任何阵列的Fortran例程正确对齐。 你可以简单地导入,并根据需要在您的.pyx文件中使用这些功能。 例如:

from scipy.linalg.cython_blas cimport dnrm2 
from scipy.linalg.cython_lapack cimport dgelsy 

考虑到这是经过严格测试,广泛使用在不同平台上运行的代码,我认为这是一个很好的候选人可靠地分发用Cython扩展,直接调用BLAS和LAPACK例程。


如果你不希望你的代码有SciPy的整体上的依赖,你可以找到许多在SciPy的的这些包装功能的相关文件linalg目录在这里 。 一个有用的参考文献是setup.py的这些线 ,其中列出的源和头文件。 请注意,Fortran编译需要!

理论上讲 ,应该可以只隔离这里的源文件需要编译BLAS和LAPACK用Cython包装,然后捆扎在一起,与你的模块的独立分机。

实践中,这是非常繁琐的事情。 对于linalg子模块的构建过程需要一些Python的功能,以帮助在不同平台上汇编(例如来自这里 )。 建筑物还依赖于其它C和Fortran源文件( 这里 ),其中所述路径是硬编码到这些Python函数。

显然,很多工作已经进入确保正确SciPy的编译在不同的操作系统和架构。

我敢肯定,这是可以做到的,但洗牌的文件约和调整路径之后,我还没有找到从SciPy的其他地区建立独立的子模块linalg这部分的正确途径。 我应该找到正确的方法,我一定会更新这个答案。



文章来源: Distributing Cython based extensions using LAPACK