首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >ctypes.POINTER( ctypes.c_int )和ctypes.c_int* 5有什么区别?

ctypes.POINTER( ctypes.c_int )和ctypes.c_int* 5有什么区别?
EN

Stack Overflow用户
提问于 2019-07-14 11:46:31
回答 1查看 822关注 0票数 1

我试图用ctype从C++调用python函数(回调)。python函数接受一个ints数组作为参数。我需要在python中访问这个数组。

C码

代码语言:javascript
复制
typedef void (*FooFunc)(int*, int*);
void runfoo(FooFunc foo_func) {
  int dims[5] = {3, 5, 1, 1, 1};
  foo_func(dims, dims);
}

python代码

代码语言:javascript
复制
def foo(dims1, dims2):
    x = dims1[0]
    y = dims1[1]
    z = dims1[2]
    print(x, y, z)
    x = dims2[0]
    y = dims2[1]
    z = dims2[2]
    print(x, y, z)


libc = ctypes.CDLL('./libpath.so')
protofoo = ctypes.CFUNCTYPE(None, ctypes.c_int * 5, ctypes.POINTER(ctypes.c_int))
libc.runfoo(protofoo(foo))

它给出(-333106720,32766,-333106720) (3,5,1)。

ctypes.c_int *5和ctypes.POINTER(ctypes.c_int)在原型中有什么区别?

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2019-07-14 20:41:02

ctypes.POINTER(ctypes.int)等同于int*

ctypes.c_int * 5是一种与int arr[5]类型等价的类型。它的实现不会作为像C这样的参数衰减到指针,所以当使用它作为参数时,它希望在堆栈上通过值传递一个数组。下面通过在C中以十六进制打印dims的地址进行了测试,您可以看到它的64位指针值是显示为十六进制时返回到python的前两个32位元素:

test.c

代码语言:javascript
复制
#include <stdio.h>
typedef void (*FooFunc)(int*, int*);
__declspec(dllexport) void runfoo(FooFunc foo_func) {
  int dims[5] = {3, 5, 1, 1, 1};
  printf("%p\n",dims);
  foo_func(dims, dims);
}

test.py

代码语言:javascript
复制
import ctypes

def foo(dims1, dims2):
    x = dims1[0]
    y = dims1[1]
    z = dims1[2]
    print(f'{x:08X} {y:08X} {z:08X}')
    x = dims2[0]
    y = dims2[1]
    z = dims2[2]
    print(f'{x:08X} {y:08X} {z:08X}')

libc = ctypes.CDLL('test')
protofoo = ctypes.CFUNCTYPE(None, ctypes.c_int * 5, ctypes.POINTER(ctypes.c_int))
libc.runfoo(protofoo(foo))

输出

代码语言:javascript
复制
000000FD6E1EED00
6E1EED00 000000FD 6E1EED00
00000003 00000005 00000001
票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/57027124

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档