python ctypes中的多维char数组(字符串数组)

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了python ctypes中的多维char数组(字符串数组)相关的知识,希望对你有一定的参考价值。

我正在尝试使用ctypes将一个字符数组数组传递给C函数。

void cfunction(char ** strings)
{
 strings[1] = "bad"; //works not what I need.
 strings[1][2] = 'd'; //this will segfault.
 return;
}

char *input[] = {"foo","bar"};
cfunction(input);

因为我抛出的数组是静态定义的,所以我只是更改了函数声明和输入参数:

void cfunction(char strings[2][4])
{
 //strings[1] = "bad"; //not what I need.
 strings[1][2] = 'd'; //what I need and now it works.
 return;
}

char input[2][4] = {"foo","bar"};
cfunction(input);

现在我遇到了如何在python中定义这个多维字符数组的问题。我以为它会这样:

import os
from ctypes import *
libhello = cdll.LoadLibrary(os.getcwd() + '/libhello.so')
input = (c_char_p * 2)()
input[0] = create_string_buffer("foo")
input[1] = create_string_buffer("bar")
libhello.cfunction(input)

这给了我TypeError: incompatible types, c_char_Array_4 instance instead of c_char_p instance。如果我将其更改为:

for i in input:
 i = create_string_buffer("foo")

然后我得到分段错误。这看起来像构建二维数组的错误方法,因为如果我打印输入,我看到None

print input[0]
print input[1]

# outputs None, None instead of "foo" and "foo"

我也遇到了使用#DEFINE MY_ARRAY_X 2#DEFINE MY_ARRAY_Y 4将数组维度保持在我的C文件中的问题,但是不知道从libhello.so中获取这些常量的好方法,以便python可以在构造时引用它们数据类型。

答案

使用类似的东西

input = ((c_char * 4) * 2)()
input[0].value = "str"
input[0][0] == "s"
input[0][1] == "t" # and so on...

用法简单:

>>> a =((c_char * 4) * 2)()
>>> a
<__main__.c_char_Array_4_Array_2 object at 0x9348d1c>
>>> a[0]
<__main__.c_char_Array_4 object at 0x9348c8c>
>>> a[0].raw
'x00x00x00x00'
>>> a[0].value
''
>>> a[0].value = "str"
>>> a[0]
<__main__.c_char_Array_4 object at 0x9348c8c>
>>> a[0].value
'str'
>>> a[0].raw
'strx00'
>>> a[1].value
''
>>> a[0][0]
's'
>>> a[0][0] = 'x'
>>> a[0].value
'xtr'

以上是关于python ctypes中的多维char数组(字符串数组)的主要内容,如果未能解决你的问题,请参考以下文章

将 ctypes int** 转换为 numpy 二维数组

使用ctypes python包装C函数返回未知大小的数组

在c中使用多维数组存储来自用户的一行,并根据字长按降序返回该行中的单词

Python ctypes 中的指针和数组

Python 3.x ctype c_wchar_p 和 c_char_p 返回状态不同于 ctypes doc

ctypes给扩展模块中的函数传递数组和结构体