Указатель с Python (ctypes) на C для сохранения вывода функции - PullRequest
0 голосов
/ 18 февраля 2019

Я новичок в C интеграции в Python.В настоящее время я обертываю библиотеку .dll в код Python, используя ctypes , и у меня возникают проблемы с передачей указателя для сохранения вывода определенной функции.

Моя функция C имеетследующая структура:

функция (int * w, int * h, unsigned short * data_output)

Где h и w - это входные данные, а data_output - массив размером (wxh, 1) .

. Мне удалось успешно интегрировать и получать результаты из функции в Matlab с помощьюсоздание массива нулей (wxh, 1) и передача его в качестве указателя с использованием libpointer ('uint16Ptr', нулей (wxh, 1)) .

Как я могу это сделать в Python?

Для других функций, где вывод был типа int * Я смог успешно получить значения, используя create_string_buffer .Но мне так и не удалось заставить его работать.

Спасибо.

1 Ответ

0 голосов
/ 19 февраля 2019

Согласно [SO]: как создать минимальный, полный и проверяемый пример (mcve) , ваш вопрос не содержит базовой информации (например, ваши попытки).Обязательно исправьте это в следующих.

Также, [Python 3]: ctypes - библиотека сторонних функций для Python .

Вот пример фиктивного примера, который иллюстрируетКонцепция.

dll.c :

#if defined(_WIN32)
#  define DLL_EXPORT __declspec(dllexport)
#else
#  define DLL_EXPORT
#endif


DLL_EXPORT int function(int w, int h, unsigned short *pData) {
    int k = 1;
    for (int i = 0; i < h; i++)
        for (int j = 0; j < w; j++, k++)
            pData[i * w + j] = k;
    return w * h;
}

code.py :

#!/usr/bin/env python3

import sys
import ctypes


DLL = "./dll.so"


def print_array(data, h, w):
    for i in range(h):
        for j in range(w):
            print("{:2d}".format(data[i * w + j]), end=" ")
    print()


def main():
    dll_dll = ctypes.CDLL(DLL)
    function_func = dll_dll.function
    function_func.argtypes = [ctypes.c_int, ctypes.c_int, ctypes.POINTER(ctypes.c_ushort)]
    function_func.restype = ctypes.c_int

    h = 3
    w = 5

    ArrayType = ctypes.c_ushort * (h * w)  # Dynamically declare the array type: `unsigned short[15]` in our case
    array = ArrayType()  # The array type instance

    print_array(array, h, w)
    res = function_func(w, h, ctypes.cast(array, ctypes.POINTER(ctypes.c_ushort)))
    print("{:} returned: {:d}".format(function_func.__name__, res))

    print_array(array, h, w)


if __name__ == "__main__":
    print("Python {:s} on {:s}\n".format(sys.version, sys.platform))
    main()

Вывод :

[cfati@cfati-5510-0:/cygdrive/e/Work/Dev/StackOverflow/q054753828]> ls
code.py  dll.c
[cfati@cfati-5510-0:/cygdrive/e/Work/Dev/StackOverflow/q054753828]> gcc -fPIC -shared -o dll.so dll.c
[cfati@cfati-5510-0:/cygdrive/e/Work/Dev/StackOverflow/q054753828]> ls
code.py  dll.c  dll.so
[cfati@cfati-5510-0:/cygdrive/e/Work/Dev/StackOverflow/q054753828]> python3 code.py
Python 3.6.4 (default, Jan  7 2018, 15:53:53)
[GCC 6.4.0] on cygwin

 0  0  0  0  0  0  0  0  0  0  0  0  0  0  0
function returned: 15
 1  2  3  4  5  6  7  8  9 10 11 12 13 14 15
...