SWIG 提供了一个文件carrays.i,它与calloc
. 您可以使用宏%array_functions
或%array_class
公开一些将 C 样式数组包装到目标语言的辅助函数。(即使您使用的是 C,您仍然可以同时使用两者)。我制作了以下界面,它my_fun
一次包装并定义了一个简单的%include
:
%module test
%include "carrays.i"
%array_functions(double,DoubleArray)
%inline %{
int my_fun(int i, void *a, void *b, void *c) {
printf("my_fun: i=%d, a=%p, b=%p, c=%p\n",i,a,b,c);
return 0;
}
%}
如果你想支持更多的类型,calloc(num, sizeof(double))
你需要在%array_functions
你的接口文件中添加更多。carrays.i 还生成用于获取和设置数组中的特定值以及删除它们的函数
之后,您的示例用法在 Python 中变为以下内容:
import test
i = 5
num = 500
num_dim = 2
a = test.new_DoubleArray(num)
b = test.new_DoubleArray(num)
c = None
if num_dim >= 3:
c = test.new_DoubleArray(num)
error = test.my_fun(i,a,b,c)
error = test.my_fun(i,None,b,None)
# Beware of the exceptions, you need a finally: really
test.delete_DoubleArray(a)
test.delete_DoubleArray(b)
test.delete_DoubleArray(c)
我在我的系统上编译并运行了它:
痛饮 -python -Wall test.i
gcc -fPIC -I/usr/include/python2.7 test_wrap.c -shared -o _test.so -Wall -Wextra
LD_LIBRARY_PATH=。python2.7运行.py
这给出了以下输出:
my_fun: i=5, a=0x2767fa0, b=0x2768f50, c=(nil)
my_fun: i=5, a=(nil), b=0x2768f50, c=(nil)
由于这里的“数组”只是在 C 中分配的真实内存块的代理,calloc
您对数组所做的任何更改都将在您下次读取它时从 Python 中可见。
如果你用Python%array_class
代替,代码变成:%array_functions
import test
i = 5
num = 500
num_dim = 2
a = test.DoubleArray(num)
b = test.DoubleArray(num)
c = None
if num_dim >= 3:
c = test.DoubleArray(num)
error = test.my_fun(i,a.cast(),b.cast(),c.cast() if c else None)
error = test.my_fun(i,None,b.cast(),None)
请注意,这里的引用计数消除了显式删除数组的需要,通过推迟引用计数来解决异常问题。%array_class
还提供了实现,因此__getitem__
它__setitem__
可以像 Python 中的任何其他数组或容器一样被下标。(虽然没有边界检查,就像 C 一样)