在cython中使用typedef的结构 [英] Using typedef'd struct in cython

查看:64
本文介绍了在cython中使用typedef的结构的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我在头文件dcm.h中具有以下定义:

I have the following definition in the header file dcm.h:

typedef struct
{    
    double alpha;
    double gamma;
    double tau;
} ThetaDCM;

我想在cython中导入它,所以我有:

I want to import it in cython, so I have:

cdef extern from "dcm.h":

    ctypedef struct ThetaDCM:

        np.float64_t alpha
        np.float64_t gamma
        np.float64_t tau

现在,我想为ThetaDCM的数组分配内存.我有以下内容:

Now I want to allocate memory to an array of ThetaDCM's. I have the following:

cdef ThetaDCM *c_theta = <ThetaDCM *> malloc(nt * nb * sizeof(ThetaDCM))

free(c_theta)

这没有编译并报告了以下错误:

This did not compile and reported the following error:

error: ‘ThetaDCM’ undeclared (first use in this function)
   __pyx_v_c_theta = ((ThetaDCM *)malloc(((__pyx_v_nt * __pyx_v_nb) * (sizeof(ThetaDCM)))));

还有其他与此错误有关的错误.如果我在extern块之外定义ThetaDCM,则代码可以毫无问题地进行编译.因此,如果我导入Theta,cython将看不到我的声明.有什么标准的方法可以解决这个问题吗?

There where other errors related to this one. If I define ThetaDCM outside the extern block, the code compiles without problem. Therefore, if I import Theta, cython cannot see my declaration. Is there any standard way to solve this?

我的文件头比我发布的头要复杂一些.是

The header of my file was a bit more complicated than what I posted. It was

# ifdef __CUDACC__
# ifndef DDM_HEADER
# define DDM_HEADER

#include "math.h"
#include "curand_kernel.h"
#include "curand.h"
#include <stdio.h>
...
# endif 

# ifdef __CUDACC__
# define BDDM_EXTERN extern "C"
# else
# define BDDM_DEVICE
# endif

BDDM_EXTERN
int llh_m0t( double *x, double *y, double *u,
    double *theta, double *ptheta, int ny, int nt, double *llh);
...
typedef struct
{    
    double alpha;
    double gamma;
    double tau;
} ThetaDCM;

# endif 

顶部的指令用于检查编译器是否为nvcc,即用于cuda代码的编译器.现在我意识到这里有一个错误,应该有:

The directive on top is used to check if the compiler is nvcc, a compiler for cuda code. Now I realize that there was an error and that I should have had:

# ifndef DDM_HEADER
# define DDM_HEADER
# ifdef __CUDACC__

#include "math.h"
#include "curand_kernel.h"
#include "curand.h"
#include <stdio.h>
...
# endif

BDDM_EXTERN
int llh_m0t( double *x, double *y, double *u,
    double *theta, double *ptheta, int ny, int nt, double *llh);
...

typedef struct
{    
    double alpha;
    double gamma;
    double tau;
} ThetaDCM;
# endif 

让我感到困惑的是,尽管有#ifdef CUDACC ,但仍编译了 cython 代码.我用cython封装了在第一个#ifdef语句(如llh_m0t)中定义的c函数,所以令人困惑的是cython可以看到这些函数定义.

What confused me is that the cython code compiled despite of the # ifdef CUDACC. I used cython to wrap c functions defined inside the first #ifdef statement (like llh_m0t), so the confusing thing is that cython could see those function definitions.

推荐答案

Cython不提供对 #define 宏的支持,以便按标题要求进行条件编译:

Cython does not provide support to #define macro for conditional compilation as required by your header:

dcm.h

# ifdef __CUDACC__

typedef struct
{    
    double alpha;
    double gamma;
    double tau;
} ThetaDCM;

# endif

一种快速的解决方法:

dcm.pyh

#define __CUDACC__
#include "dcm.h"


dcm.pyx

[...]

cdef extern from "dcm.pyh":
#                     ^^^
    [...]

这篇关于在cython中使用typedef的结构的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆