繁体   English   中英

提高 Python 中的 FFT 性能

[英]Improving FFT performance in Python

Python 中最快的 FFT 实现是什么?

似乎 numpy.fft 和 scipy.fftpack 都是基于 fftpack,而不是 FFTW。 fftpack 和 FFTW 一样快吗? 使用多线程 FFT 或使用分布式 (MPI) FFT 怎么样?

您当然可以使用 Cython 或其他允许您访问外部库的类似工具来包装您想要测试的任何 FFT 实现。

基于GPU

如果您要测试 FFT 实现,您还可以查看基于 GPU 的代码(如果您可以访问适当的硬件)。 有几个: reikna.fftscikits.cuda

基于CPU

还有一个基于 CPU 的 python FFTW 包装器pyFFTW

(也有pyFFTW3 ,但它不像 pyFFTW 那样积极维护,而且它不适用于 Python3。(来源))

我对这些都没有经验。 如果速度对您很重要,您可能需要为您的特定应用程序进行一些挖掘和基准测试不同的代码。

对于https://gist.github.com/fnielsen/99b981b9da34ae3d5035的详细测试,我发现 scipy.fftpack 与我通过pyfftw.interfaces.scipy_fftpack简单应用 pyfftw 相比表现良好,除了具有对应于长度的素数的数据数字。

似乎有一些与第一次调用 pyfftw.interfaces.scipy_fftpack.fft 相关的设置成本。 第二次速度更快。 Numpy 和 scipy 的带有质数的 fftpack 对于我尝试的数据大小表现非常糟糕。 在这种情况下,CZT 更快。 几个月前在 Scipy 的 Github 上提出了一个关于这个问题的问题,请参阅https://github.com/scipy/scipy/issues/4288

20000 prime=False
  padded_fft : 0.003116
   numpy_fft : 0.003502
   scipy_fft : 0.001538
         czt : 0.035041
    fftw_fft : 0.004007
------------------------------------------------------------
20011 prime=True
  padded_fft : 0.001070
   numpy_fft : 1.263672
   scipy_fft : 0.875641
         czt : 0.033139
    fftw_fft : 0.009980
------------------------------------------------------------
21803 prime=True
  padded_fft : 0.001076
   numpy_fft : 1.510341
   scipy_fft : 1.043572
         czt : 0.035129
    fftw_fft : 0.011463
------------------------------------------------------------
21804 prime=False
  padded_fft : 0.001108
   numpy_fft : 0.004672
   scipy_fft : 0.001620
         czt : 0.033854
    fftw_fft : 0.005075
------------------------------------------------------------
21997 prime=True
  padded_fft : 0.000940
   numpy_fft : 1.534876
   scipy_fft : 1.058001
         czt : 0.034321
    fftw_fft : 0.012839
------------------------------------------------------------
32768 prime=False
  padded_fft : 0.001222
   numpy_fft : 0.002410
   scipy_fft : 0.000925
         czt : 0.039275
    fftw_fft : 0.005714
------------------------------------------------------------

pyFFTW3 package 比 pyFFTW 库差,至少在实现方面是这样。 因为它们都包装了 FFTW3 库,所以我猜速度应该是一样的。

https://pypi.python.org/pypi/pyFFTW

在我工作的地方,一些研究人员编译了这个 Fortran 库,它针对特定问题设置和调用 FFTW。 这个 Fortran 库(带有一些子程序的模块)需要来自我的 Python 程序的一些输入数据(二维列表)。

我所做的是为 Python 创建一个小的 C 扩展,包装 Fortran 库,我基本上调用“init”来设置 FFTW 规划器,另一个 function 来提供我的二维列表(数组),以及一个“计算”function。

创建 C 扩展是一项小任务,并且有很多针对该特定任务的优秀教程。

这种方法的好处是我们获得了速度……很多速度。 唯一的缺点是在 C 扩展中,我们必须迭代 Python 列表,并将所有 Python 数据提取到 memory 缓冲区中。

FFTW 站点显示 fftpack 的运行速度大约是 FFTW 的 1/3,但这是机械翻译的 Fortran-to-C 步骤,然后是 C 编译,我不知道 numpy/scipy 是否使用更直接的 Fortran 编译。 如果性能对您至关重要,您可以考虑将 FFTW 编译成 DLL/共享库并使用 ctypes 访问它,或者构建自定义 C 扩展。

FFTW3 似乎是最快的可用实现,并且包装得很好。 第一个答案中的 PyFFTW 绑定有效。 下面是一些比较执行时间的代码: test_ffts.py

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM