gpt4 book ai didi

python - 在 SWIG 中返回未指定大小的 numpy 数组

转载 作者:太空宇宙 更新时间:2023-11-04 00:03:26 25 4
gpt4 key购买 nike

我的目标是将 SWIG 与 C 和 Python 结合使用来创建一个函数,该函数将 NumPy 数组作为输入并返回一个不同的 NumPy 数组。返回的数组具有一些未指定的大小,具体大小取决于输入数组。不幸的是,当我尝试运行我的代码时,我得到了一个空数组。这是一个显示问题的“最小”示例。我通过以下方式运行此代码:

python setup.py build_ext --inplace
python test.py

感兴趣的文件复制如下。如果您知道如何使这段代码返回一个非空的 NumPy 数组,请告诉我。谢谢!

取消条款.c:

#include "cancelterms.h"
void cancel(double complex* vec, int m, int n, double complex sum[])
{

// Some code that processes vec.

// This is just an example. In practice the following lines will depend on vec.
sum[0] = 1.0;
sum[1] = 2.5;
sum[2] = 3.6;
}

取消条款.h:

#include <stdlib.h>
#include <stdio.h>
#include <complex.h>

void cancel(double complex* vec, int m, int n, double complex sum[]);

取消条款.i:

%module cancelterms
%{
/* Put header files here or function declarations like below */
#define SWIG_FILE_WITH_INIT
#include "cancelterms.h"
%}

%include "numpy.i"
%include <complex.i>

%numpy_typemaps(double complex, NPY_CDOUBLE, int)

%init %{
import_array();
%}

%apply (double complex* INPLACE_ARRAY2, int DIM1, int DIM2) {(double complex* vec, int m, int n)}
%apply (double complex ARGOUT_ARRAY1[ANY]) {(double complex sum[])}

%include "cancelterms.h"

设置.py:

# Import necessary modules.
from distutils.core import setup, Extension
import numpy as np

try:
numpy_include = np.get_include()
except AttributeError:
numpy_include = np.get_numpy_include()

example_module = Extension('_cancelterms', sources=['cancelterms.c', 'cancelterms.i'], include_dirs = [numpy_include])

setup(name='cancelterms', ext_modules=[example_module], py_modules=["cancelterms"])

测试.py:

import cancelterms
import numpy as np

a=np.array([[1.0j,2.0j,3.0j,4.0j,5.0j,6.0j],[-1.0j,-2.0j,-3.0j,6.0j,7.0j,8.0j]])
print cancelterms.cancel(a)

不幸的是,numpy.i 太大而无法粘贴到此处,但我使用了 numpy github 存储库中的标准 numpy.i 文件,并进行了一些小的修改,我将 double complex 添加到类型列表中。

最佳答案

...[ANY] 类型映射适用于具有硬编码维度 的数组。 numpy.i docs 中明确说明了这一点用于输入数组,但也适用于其他数组。

例如,它们可以用作:

%apply (double complex ARGOUT_ARRAY1[ANY]) {(double complex sum[5])}

如果您的函数采用大小为 5 的数组(由调用者/在包装代码中分配)。

重点是 SWIG 无法知道 argout 数组 sum 的大小。您的代码完全可以编译和运行纯属巧合。查看生成的包装器代码(搜索“wrap_cancel”),您将看到发生了什么。

还有以下类型映射:

  • ( DATA_TYPE*​​ ARGOUT_ARRAY1, int DIM1 )
    您可以在其中指定要预分配的数组的大小
  • ( DATA_TYPE*​​ ARGOUTVIEW_ARRAY1, DIM_TYPE*​​ DIM1 )
    其中数组由函数分配,但另外返回分配数组的大小。

在您的例子中,函数 cancel 为数组 sum 分配内存,假设调用者有某种方法计算出大小。这种情况下没有预定义的类型映射。

这类似于函数仅返回 double complex * 的情况,如 numpy.i 文档中所述:

If you run into a situation where a function or method is returning a pointer to an array, your best bet is to write your own version of the function to be wrapped, either with %extend for the case of class methods or %ignore and %rename for the case of functions.

关于python - 在 SWIG 中返回未指定大小的 numpy 数组,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33687079/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com