使用Cython评估numpy网格上的C函数

时间:2011-10-19 22:55:20

标签: python numpy cython

Simple wrapping of C code with cython中的示例很好地描述了如何在从numpy传递的数组上计算用C编写的函数,并将结果返回到numpy数组中。

如何做同样的事情却返回2D阵列?即我想评估由两个numpy数组定义的网格上的C函数,并将结果作为numpy 2D数组返回。

这将是这样的(使用与上面的链接相同的功能)。显然现在不能使用双z [],但我不确定如何将2D numpy数组传递给C.

/*  fc.cpp    */
int fc( int N, const double a[], const double b[], double z[] )
    {
    for( int i = 0;  i < N;  i ++ ){
        for( int j = 0;  j < N;  j ++ ){
            z[i][j] = somefunction(a[i],b[j]);
    }
    return N;
}

这是原始的.pyx文件(见下文)。

import numpy as np
cimport numpy as np
cdef extern from "fc.h": 
    int fc( int N, double* a, double* b, double* z )  # z = a + b

def fpy( N,
    np.ndarray[np.double_t,ndim=1] A,
    np.ndarray[np.double_t,ndim=1] B,
    np.ndarray[np.double_t,ndim=1] Z ):
    """ wrap np arrays to fc( a.data ... ) """
       assert N <= len(A) == len(B) == len(Z)
       fcret = fc( N, <double*> A.data, <double*> B.data, <double*> Z.data )

    return fcret

非常感谢。

1 个答案:

答案 0 :(得分:1)

您可以将正常数组用于2D矩阵。您只需要为函数指定维度的长度。

在C文件中执行以下操作: (z现在是一个长度为N * N的数组)

int fc( int N, const double a[], const double b[], double z[] )
{
    for( int i = 0;  i < N;  i++ ){
        for( int j = 0;  j < N;  j ++ ){
            z[(i*N)+j] = somefunction(a[i],b[j]);
    }
    return N;
}

在Python中你需要做同样的事情,所以你可以使用带有N * N个元素的一维数组而不是二维矩阵。

更新3D案例

(z现在是长度为N * N * N的数组)

int fc( int N, const double a[], const double b[],const double c[], double z[] )
{
    for( int i = 0;  i < N;  i++ ){
        for( int j = 0;  j < N;  j ++ ){
           for( int k = 0;  k < N;  k ++ ){
            z[((i*N)+j)*N+k] = somefunction(a[i],b[j],c[k]);
    }
    return N;
}