gpt4 book ai didi

python - Cython 创建 C 函数别名

转载 作者:行者123 更新时间:2023-11-30 03:15:52 28 4
gpt4 key购买 nike

我有两个函数变体:void func1(double *)void func2(double *),它们是从 C++ 代码中提取出来的。

我希望能够编写一个包装它们的函数或映射:

cdef func_alias(int choice):
if choice == 0:
return func1
elif choice == 1:
return func2

但是编译无法将'void (double *) nogil'转换为Python对象

或者,我尝试使用产生相同错误的字典:

cdef dict func_dict = {0: func1, 1: func2}

但我得到了同样的错误。

我不确定我是否可以按照以下方式做一些事情

from libcpp.map import map
cdef map[int, void] func_map = {0: func1, 1: func2}

这导致 Cannot interpret dict as type 'map[int,void]'

最佳答案

您的 func_alias 函数没有定义返回类型(这意味着它将默认为 python 对象)。由于函数指针不是有效的 python 对象,cython 会在编译时给出错误消息。我们可以定义一个表示函数指针的 ctypedef 并将其用作返回类型。这是一个这样做的例子:

ctypedef void (* double_func)(double *)

cdef void func_1(double *arg1):
print(1, arg1[0])

cdef void func_2(double *arg1):
print(2, arg1[0])

cdef double_func func_alias(int choice):
if choice == 1:
return func_1
elif choice == 2:
return func_2

cdef double test_input = 3.14
func_alias(1)(&test_input)
func_alias(2)(&test_input)

附带说明一下,如果您只有固定数量的潜在函数指针需要考虑,我会考虑使用枚举代替 if 语句。如果有帮助,我可以举一个例子。如果有任何不清楚的地方,请告诉我。

更新:查看问题的第二部分,我发现您也在考虑使用 HashMap 将整数映射到函数指针。虽然您不能使用 dict 来执行此操作,因为它们只能存储 python 对象,但您可以使用 map(或 unordered_map,它应该表现稍好)。不幸的是,您不能使用方便的 python dict 语法来初始化 dict 的所有值,而必须一项一项地添加。这是实际的方法:

from libcpp.unordered_map cimport unordered_map

ctypedef void (* double_func)(double *)
cdef unordered_map[int, double_func] func_map
func_map[1] = func_1
func_map[2] = func_2

cdef void func_1(double *arg1):
print(1, arg1[0])

cdef void func_2(double *arg1):
print(2, arg1[0])

cdef double_func func_alias(int choice):
return func_map[choice]

cdef double test_input = 3.14
func_alias(1)(&test_input)
func_alias(2)(&test_input)

关于python - Cython 创建 C 函数别名,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56708159/

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