具有融合类型输入的 Cython 函数指针:融合类型的使用无效,类型无法专门化

问题描述 投票:0回答:1

与之前的post不同,我在这里使用所有cdef函数。如果我使用 fused_type 输入的函数指针,它将引发“融合类型的无效使用,类型无法专门化”。相反,内置类型的函数指针效果很好。为什么?

cimport cython


# raise error
ctypedef fused fused_type:
   float
   int

ctypedef fused_type (* _func_pointer) (fused_type[:])

cdef fused_type base_func(fused_type[:] arg1):
   return arg1[0]

cdef fused_type c_entry(fused_type[:] arg1, _func_pointer func):
   return func(arg1)

cdef fused_type base_wrapper(fused_type[:] arg1):
   return c_entry(arg1, base_func)

""" -------   """
# works
cdef int base_func(int[:] arg1):
   return arg1[0]

cdef int c_entry(int[:] arg1, _func_pointer func):
   return func(arg1)

cdef int base_wrapper(int[:] arg1):
   return c_entry(arg1, base_func)

python cython static-typing
1个回答
0
投票

您需要将其更改为

cdef fused_type base_wrapper(fused_type[:] arg1):
   return c_entry(arg1, base_func[fused_type])

base_wrapper
被专门化时,无论
base_func
当前位于
fused_type
中,都会选择
base_wrapper
的专门化。


原因的粗略解释:

ctypedef fused_type (* _func_pointer) (fused_type[:])

这没有定义接受并返回

fused_type
的函数指针类型。相反,它定义了一个包含两种类型的融合类型:

float (*)(float[:])
int (*)(int[:])

当您单独执行

base_func
时,它不是一个“真正的”函数 - 您可以通过调用它或我手动选择它来获得其中一个专业化(例如
base_func[int]
)。

因此,在

base_wrapper
中,
return c_entry(arg1, base_func)
行不知道它应该使用
base_func
的哪种专业化,因此无法选择它应该匹配的
_func_pointer
的两种类型中的哪一种。

Cython 融合类型系统相当垃圾,并没有花太多精力来解决混淆 - 它要么是明确的完全匹配,要么根本不匹配。

© www.soinside.com 2019 - 2024. All rights reserved.