使用 F2PY #

此页面包含对命令的所有命令行选项的参考f2py ,以及对numpy.f2py 模块内部功能的参考。

用作f2py命令行工具#

当用作命令行工具时,具有三种主要模式,通过和开关的f2py使用来区分。-c-h

1.签名文件生成#

要扫描 Fortran 源代码并生成签名文件,请使用

f2py -h <filename.pyf> <options> <fortran files>   \
  [[ only: <fortran functions>  : ]                \
    [ skip: <fortran functions>  : ]]...           \
  [<fortran files> ...]

笔记

Fortran 源文件可以包含许多例程,并且通常没有必要允许所有例程都可从 Python 使用。在这种情况下,指定应包装哪些例程(在该部分中)或 F2PY 应忽略哪些例程(在该部分中)。only: .. :skip: .. :

如果<filename.pyf>指定为stdout,则签名将写入标准输出而不是文件。

在其他选项(见下文)中,可以在此模式下使用以下选项:

--overwrite-signature

覆盖现有的签名文件。

2.扩展模块搭建#

要构建扩展模块,请使用

f2py -m <modulename> <options> <fortran files>   \
  [[ only: <fortran functions>  : ]              \
    [ skip: <fortran functions>  : ]]...          \
  [<fortran files> ...]

构建的扩展模块保存到<modulename>module.c当前目录。

这里还可能包含签名文件。除其他选项(见下文)外,在此模式下可以使用以下选项:<fortran files>

--debug-capi

向扩展模块添加调试挂钩。使用此扩展模块时,有关包装器的各种诊断信息将写入标准输出,例如变量的值、采取的步骤等。

-include'<includefile>'

将 CPP#include语句添加到扩展模块源。 <includefile>应以下列形式之一给出

"filename.ext"
<filename.ext>

include 语句插入到包装函数之前。此功能允许<includefile>在 F2PY 生成的包装器中使用任意 C 函数(在 中定义)。

笔记

此选项已弃用。使用usercode语句直接在签名文件中指定C代码片段。

--[no-]wrap-functions

创建 Fortran 函数的 Fortran 子例程包装器。 --wrap-functions是默认值,因为它确保最大的可移植性和编译器独立性。

--include-paths <path1>:<path2>:..

搜索给定目录中的包含文件。

--help-link [<list of resources names>]

列出 找到的系统资源numpy_distutils/system_info.py。例如,尝试.f2py --help-link lapack_opt

3. 构建模块#

要构建扩展模块,请使用

f2py -c <options> <fortran files>       \
  [[ only: <fortran functions>  : ]     \
    [ skip: <fortran functions>  : ]]... \
  [ <fortran/c source files> ] [ <.o, .a, .so files> ]

如果包含签名文件,则构建扩展模块的源代码,编译所有 Fortran 和 C 源代码,最后将所有对象和库文件链接到 保存到当前目录中的扩展模块。<fortran files><modulename>.so

如果不包含签名文件,则在继续构建扩展模块之前,通过扫描所有 Fortran 源代码中的例程签名来构建扩展模块。<fortran files>

在其他选项(见下文)和先前模式中描述的选项中,可以在此模式中使用以下选项:

--help-fcompiler

列出可用的 Fortran 编译器。

--help-compiler [已折旧]

列出可用的 Fortran 编译器。

--fcompiler=<Vendor>

由供应商指定 Fortran 编译器类型。

--f77exec=<path>

指定 F77 编译器的路径

--fcompiler-exec=<path> [已折旧]

指定 F77 编译器的路径

--f90exec=<path>

指定 F90 编译器的路径

--f90compiler-exec=<path> [已折旧]

指定 F90 编译器的路径

--f77flags=<string>

指定 F77 编译器标志

--f90flags=<string>

指定 F90 编译器标志

--opt=<string>

指定优化标志

--arch=<string>

指定架构特定的优化标志

--noopt

不带优化标志的编译

--noarch

不使用依赖于架构的优化标志进行编译

--debug

使用调试信息进行编译

-l<libname>

<libname>链接时使用库。

-D<macro>[=<defn=1>]

将宏定义<macro><defn>.

-U<macro>

定义宏<macro>

-I<dir>

将目录追加<dir>到搜索包含文件的目录列表中。

-L<dir>

将目录添加<dir>到要搜索的目录列表中 -l

link-<resource>

将扩展模块与 <resource> 链接,如 所定义 numpy_distutils/system_info.py。例如,要链接优化的 LAPACK 库(MacOSX 上的 vecLib,其他地方的 ATLAS),请使用--link-lapack_opt.另请参阅--help-link开关。

笔记

该选项必须应用于现有文件(加上源/对象/库文件),或者必须指定该 选项(加上源/对象/库文件)。使用以下选项之一:f2py -c.pyf-m <modulename>

f2py -c -m fib1 fib1.f

或者

f2py -m fib1 fib1.f -h fib1.pyf
f2py -c fib1.pyf fib1.f

有关详细信息,请参阅构建 C 和 C++ 扩展Python 文档。

构建扩展模块时,非 gcc Fortran 编译器可能需要以下宏的组合:

-DPREPEND_FORTRAN
-DNO_APPEND_FORTRAN
-DUPPERCASE_FORTRAN

要测试 F2PY 生成的接口的性能,请使用 -DF2PY_REPORT_ATEXIT.然后在Python的出口处打印出各种计时的报告。此功能可能不适用于所有平台,目前仅支持 Linux。

要查看 F2PY 生成的接口是否执行数组参数的副本,请使用 -DF2PY_REPORT_ON_ARRAY_COPY=<int>。当数组参数的大小大于 时<int>,将向 发送有关复制的消息stderr

其他选项#

-m <modulename>

扩展模块的名称。默认为untitled.

警告

*.pyf如果使用签名文件 ( ),请勿使用此选项。

--[no-]lower

不要[不]降低 中的大小写。默认情况下,假定带开关,不带开关。<fortran files>--lower-h--no-lower-h

-include<header>

在 C 包装器中写入附加标头,可以多次传递,每次生成 #include <header>。请注意,这意味着用单引号传递并且不带空格,例如'-include<stdbool.h>'

--build-dir <dirname>

所有 F2PY 生成的文件都是在<dirname>.默认为 tempfile.mkdtemp().

--f2cmap <filename>

KIND从给定文件加载 Fortran 到 C规范。

--quiet

安静地跑。

--verbose

以额外的冗长方式运行。

--skip-empty-wrappers

除非输入需要,否则不要生成包装文件。这是一个向后兼容标志,用于恢复 1.22.4 之前的行为。

-v

打印 F2PY 版本并退出。

在不带任何选项的情况下执行f2py以获得可用选项的最新列表。

Python 模块numpy.f2py#

f2py 程序是用 Python 编写的,可以从代码内部运行以在运行时编译 Fortran 代码,如下所示:

from numpy import f2py
with open("add.f") as sourcefile:
    sourcecode = sourcefile.read()
f2py.compile(sourcecode, modulename='add')
import add

源字符串可以是任何有效的 Fortran 代码。如果您想保存扩展模块源代码,则可以通过source_fn关键字向编译函数提供合适的文件名。

作为模块使用时numpy.f2py,可以调用以下函数。

警告

目前该f2py模块的 Python 接口并不成熟,将来可能会发生变化。

Fortran 到 Python 接口生成器。

numpy.f2py。编译( source , modulename = 'untitled' , extra_args = '' , verbose = True , source_fn = None ,扩展名= '.f' , full_output = False ) [source] #

使用 f2py 从 Fortran 77 源字符串构建扩展模块。

参数
str 或字节

要编译的模块/子程序的 Fortran 源代码

版本 1.16.0 中更改:接受 str 以及 bytes

模块名str,可选

编译后的python模块的名称

extra_args字符串或列表,可选

传递给 f2py 的附加参数

版本 1.16.0 中的更改:还可以提供参数列表。

详细布尔值,可选

将 f2py 输出打印到屏幕

source_fn str,可选

写入 Fortran 源代码的文件的名称。默认是使用参数提供扩展名的临时extension文件

扩展,可选{'.f', '.f90'}

如果未提供source_fn ,则文件扩展名。该扩展告诉我们使用哪个 Fortran 标准。默认为.f,表示 F77 标准。

1.11.0 版本中的新增内容。

full_output布尔值,可选

如果为 True,则返回subprocess.CompletedProcess包含编译过程的 stdout 和 stderr 的 a,而不仅仅是状态代码。

1.20.0 版本中的新增功能。

返回
结果int 或subprocess.CompletedProcess

0 表示成功,或者subprocess.CompletedProcessif full_output=True

例子

>>> import numpy.f2py
>>> fsource = '''
...       subroutine foo
...       print*, "Hello world!"
...       end 
... '''
>>> numpy.f2py.compile(fsource, modulename='hello', verbose=0)
0
>>> import hello
>>> hello.foo()
 Hello world!
numpy.f2py。get_include ( ) [来源] #

fortranobject.c返回包含和文件的目录.h

笔记

numpy.distutils当直接使用.f和/或.pyf文件一次性构建扩展时,不需要此函数 。

使用 f2py 生成的代码构建的 Python 扩展模块需要用作 fortranobject.c源文件,并包含fortranobject.h 标头。该函数可用于获取包含这两个文件的目录。

返回
include_path字符串

fortranobject.c包含和 的 目录的绝对路径fortranobject.h

也可以看看

numpy.get_include

返回 numpy 包含目录的函数

笔记

版本 1.21.1 中的新增功能。

除非您使用的构建系统对 f2py 有特定支持,否则使用.pyf签名文件构建 Python 扩展是一个两步过程。对于模块mymod

  • 第1步:运行。这会在 . 旁边生成和 (如果需要) 文件。python -m numpy.f2py mymod.pyf --quiet_mymodmodule.c_fblas-f2pywrappers.fmymod.pyf

  • 第 2 步:构建 Python 扩展模块。这需要以下源文件:

    • _mymodmodule.c

    • _mymod-f2pywrappers.f(如果是在步骤 1 中生成的)

    • fortranobject.c

numpy.f2py。run_main ( comline_list ) [来源] #

相当于运行:

f2py <args>

其中,但是在 Python 中。除非 使用 ,否则此函数返回一个字典,其中包含有关生成的模块及其对源文件的依赖关系的信息。<args>=string.join(<list>,' ')-h

您不能使用此功能构建扩展模块,即-c不允许使用。请改用该compile命令。

例子

该命令可以从 Python 执行,如下所示。f2py -m scalar scalar.f

>>> import numpy.f2py
>>> r = numpy.f2py.run_main(['-m','scalar','doc/source/f2py/scalar.f'])
Reading fortran codes...
        Reading file 'doc/source/f2py/scalar.f' (format:fix,strict)
Post-processing...
        Block: scalar
                        Block: FOO
Building modules...
        Building module "scalar"...
        Wrote C/API module "scalar" to file "./scalarmodule.c"
>>> print(r)
{'scalar': {'h': ['/home/users/pearu/src_cvs/f2py/src/fortranobject.h'],
	 'csrc': ['./scalarmodule.c', 
                  '/home/users/pearu/src_cvs/f2py/src/fortranobject.c']}}

自动生成扩展模块#

如果您想分发 f2py 扩展模块,则只需包含 .pyf 文件和 Fortran 代码。 NumPy 中的 distutils 扩展允许您完全根据此接口文件定义扩展模块。setup.py允许分发模块的有效文件add.f(作为包的一部分 f2py_examples,以便将其加载为f2py_examples.add)是:

def configuration(parent_package='', top_path=None)
    from numpy.distutils.misc_util import Configuration
    config = Configuration('f2py_examples',parent_package, top_path)
    config.add_extension('add', sources=['add.pyf','add.f'])
    return config

if __name__ == '__main__':
    from numpy.distutils.core import setup
    setup(**configuration(top_path='').todict())

新软件包的安装很容易使用:

pip install .

假设您有适当的权限写入您正在使用的 Python 版本的主站点包目录。为了使生成的包正常工作,您需要创建一个名为__init__.py (与 位于同一目录中add.pyf)的文件。请注意,扩展模块完全根据add.pyfadd.f文件定义。 .pyf 文件到 .c 文件的转换由numpy.distutils.