如何确定cython中指针变量中元素的数量?如果指针指向sizeof(ptr)/sizeof(int)
变量,我在C中看到单向似乎是int
。但这似乎不适用于cython。例如。当我试图将两个内存视图连接到一个指针时,如下所示:
from libc.stdlib cimport malloc, free
cdef int * join(int[:] a, int[:] b):
cdef:
int n_a = a.shape[0]
int n_b = b.shape[0]
int new_size = n_a + n_b
int *joined = <int *> malloc(new_size*sizeof(int))
int i
try:
for i in range(n_a):
joined[i] = a[i]
for i in range(n_b):
joined[n_a+i] = b[i]
return joined
finally:
free(joined)
@cython.cdivision(True)
def join_memviews(int[:] n, int[:] m):
cdef int[:] arr_fst = n
cdef int[:] arr_snd = m
cdef int *arr_new
cdef int new_size
arr_new = join(arr_fst,arr_snd)
new_size = sizeof(arr_new)/sizeof(int)
return [arr_new[i] for i in range(new_size)]
从python脚本调用join_memviews
时,我得不到所需的结果,例如:
# in python
a = np.array([1,2])
b = np.array([3,4])
a_b = join_memviews(a,b)
我也尝试使用类型
DTYPE = np.int
ctypedef np.int_t DTYPE_t
作为sizeof()
内部的争论,但这也不起作用。
编辑:指针变量的处理显然对我来说有点粗心。我希望以下情况很好(即使这可能不是一种谨慎的做法):
cdef int * join(int[:] a, int[:] b, int new_size):
cdef:
int *joined = <int *> malloc(new_size*sizeof(int))
int i
for i in range(n_a):
joined[i] = a[i]
for i in range(n_b):
joined[n_a+i] = b[i]
return joined
def join_memviews(int[:] n, int[:] m):
cdef int[:] arr_fst = n
cdef int[:] arr_snd = m
cdef int *arr_new
cdef int new_size = n.shape[0] + m.shape[0]
try:
arr_new = join(arr_fst,arr_snd, new_size)
return [arr_new[i] for i in range(new_size)]
finally:
free(arr_new)
答案 0 :(得分:0)
你做不到。它在C中也不起作用。 sizeof(ptr)
返回用于存储指针的内存量(通常为4或8,具体取决于您的系统),而不是数组的长度。您需要手动跟踪malloc
ed数组的长度。
此外,以下代码是灾难的处方:
cdef int *joined = <int *> malloc(new_size*sizeof(int))
try:
return joined
finally:
free(joined)
free
会在函数退出时立即发生,因此会向调用函数返回一个无效指针。
您应该使用正确管理的Python数组(来自numpy或标准库array
模块),除非您绝对无法避免。