目的
将结构数组从python模块传递到c模块。
方法
利用python ctypes调用c api来传输数据。
步骤
C API声明
injectNodes(int nodeNum, struct node *pNode);
struct node {
uint16_t id;
uint8_t version;
uint8_t depth;
};
Python代码
#!/bin/python3
import pdb
from ctypes import *
class Node(Structure):
_field_ = [
("id", c_uint16),
("version", c_uint8),
("depth", c_uint8)
]
dics = [{'ID': '3', 'VERSION': '180', 'DEPTH': '924'},
{'ID': '9', 'VERSION': '180', 'DEPTH': '269'},
{'ID': '2', 'VERSION': '180', 'DEPTH': '537'}]
nodeNum = len(dics)
NODES = Node * nodeNum
nodes = NODES()
for j in range(nodeNum):
print(dics[j])
node = Node()
node.id = int(dics[j]["ID"])
node.version = int(dics[j]["VERSION"])
node.depth = int(dics[j]["DEPTH"])
print("id", node.id)
print("version", node.version)
print("depth", node.depth)
nodes[j] = node
print("id", nodes[j].id)
print("version", nodes[j].version)
print("depth", nodes[j].depth)
print(nodes)
预期结果
{'ID': '3', 'DEPTH': '924', 'VERSION': '180'}
id 3
version 180
depth 924
id 3
version 180
depth 924
{'ID': '9', 'DEPTH': '269', 'VERSION': '180'}
id 9
version 180
depth 269
id 9
version 180
depth 269
{'ID': '2', 'DEPTH': '537', 'VERSION': '180'}
id 2
version 180
depth 537
id 2
version 180
depth 537
实际结果
{'ID': '3', 'DEPTH': '924', 'VERSION': '180'}
id 3
version 180
depth 924
Traceback (most recent call last):
File "array_test.py", line 28, in <module>
print("id", nodes[j].id)
AttributeError: 'Node' object has no attribute 'id'
答案 0 :(得分:0)
Structure
必须具有_fields_
而不是__field__
的定义。
还有另一个错误。 depth
被声明为c_uint8
,范围为0-255,但是字典中的值都大于255。
我建议在结构中定义__repr__
,以便Node
可以打印自身,并使用更多的“ pythonic”循环:
from ctypes import *
class Node(Structure):
_fields_ = [("id", c_uint16),
("version", c_uint8),
("depth", c_uint8)]
def __repr__(self):
return f'Node(id={self.id}, version={self.version}, depth={self.depth})'
dics = [{'ID': '3', 'VERSION': '180', 'DEPTH': '924'},
{'ID': '9', 'VERSION': '180', 'DEPTH': '269'},
{'ID': '2', 'VERSION': '180', 'DEPTH': '537'}]
nodeNum = len(dics)
NODES = Node * nodeNum
nodes = NODES()
for node,dic in zip(nodes,dics):
node.id = int(dic['ID'])
node.version = int(dic['VERSION'])
node.depth = int(dic['DEPTH'])
for node in nodes:
print(node)
输出(由于depth
的定义,c_uint8
是模块256):
Node(id=3, version=180, depth=156)
Node(id=9, version=180, depth=13)
Node(id=2, version=180, depth=25)