使用ctypes通过引用传递整数数组

时间:2019-03-13 15:49:59

标签: python c++ arrays ctypes

我想从python运行C ++函数,该函数通过引用返回int*数组并将其转换为python列表。

这是示例C ++代码:

#include "stdafx.h"
#include <iostream>

#define DLLEXPORT extern "C" __declspec(dllexport)

DLLEXPORT int getResponse(int*& hash_list)
{

    std::cout << hash_list << std::endl;

    int* hashes = new int[3];
    hashes[0] = 8;
    hashes[1] = 9;
    hashes[2] = 10;
    hash_list = hashes;

    std::cout << hash_list << std::endl;
    std::cout << *hash_list << std::endl;
    std::cout << *(hash_list + 1) << std::endl;
    std::cout << *(hash_list + 2) << std::endl;

    return 0;
}

DLLEXPORT void testDLL()
{
    std::cout << "DLL can be read" << std::endl;
}

这是我在python中的最佳尝试:

from ctypes import cdll, c_int, POINTER, ARRAY, byref

LIB = cdll.LoadLibrary("<path to DLL>")

LIB.testDLL()

func = LIB.getResponse
itype = c_int
func.argtypes = [POINTER(ARRAY(itype,3))]
func.restype = c_int

chashes = (itype * 3)(*[0,1,2])
print(chashes)

func(byref(chashes))

print(chashes)
print(list(chashes))

这是输出:

DLL can be read
<ctypes.c_long_Array_3 object at 0x000001B00FB7FEC8>
0000000100000000
000001B00DB0AC70
8
9
10
<ctypes.c_long_Array_3 object at 0x000001B00FB7FEC8>
[229682288, 432, 2]

这种方法似乎取得了一些成功,但是我认为传递给C ++函数的初始数组具有无效的条目。然后无论如何都将返回的值修改。

ctypes是否可能?任何建议,将不胜感激。

我还尝试使用c_void_p代替ARRAY。在那种情况下,它似乎也可以工作,但是我不知道如何将结果指针变成python列表。

1 个答案:

答案 0 :(得分:1)

ctypes访问C接口。 C没有指针引用,但是当被当作extern "C"时,指针引用与指针指针一样被封送。只是不要从Python传递None,因为C ++会将其视为空引用。您最好实际上声明该函数采用int**,以便处理可能从Python传递None的可能性。

使用:

func.argtypes = [POINTER(POINTER(c_int))]

致电:

p = POINTER(c_int)()
func(byref(p))
print(p[:3])