从 numpy 数组获取指针以将图像发送到 C++

Posted

技术标签:

【中文标题】从 numpy 数组获取指针以将图像发送到 C++【英文标题】:Get pointer from numpy array to send image to C++ 【发布时间】:2018-06-26 07:08:22 【问题描述】:

我正在处理一个项目,我必须处理 PythonC++ 之间的图像。为了将图像从 C++ 发送到 Python,我在图像的第一个像素上发送了一个指针(作为来自 OpenCV 库的 Mat 对象),在带有两个 for 循环的 Python 中,我使用这个指针创建了一个 2D numpy 数组。

但我没有成功以另一种方式做同样的事情:获取 numpy 2D 数组(图像)的第一个像素的内存地址并将其传递给 C++。

假设 x 是我的图像(2D numpy 数组),我尝试了如下解决方案:

x.__array_interface__['data'][0] 但这给出了一个整数,而不是地址 x.data 每次调用它时都会给出不同的值,因为它给了我一个临时缓冲区的地址,而不是图像本身

提前感谢您的任何建议/帮助。

【问题讨论】:

“在 Python 和 C++ 之间发送图像” 到底是什么意思?您使用的是套接字、消息队列还是某种类型的共享内存? 我想在 Python 中读取图像,并将其发送到 C++ 以在 C++ 上执行操作。所以我必须找到一种方法来做到这一点,为此我使用了一个指针。但我找到了使用#ralf answer的方法。 【参考方案1】:

我找到了一种“简单”的方法:

C++ 中,函数必须将 void * ptr 作为参数,这样我可以使用 Python 发送的指针创建一个 Mat 对象:

void myCfunction(void* ptr)
    Mat matrix = Mat(sizes, CV_8UC1, (uchar*)ptr);

并且,在 Python 中,使用__array_interface__ 获取内存地址(int 类型,很奇怪):

mydll.myFunction(myNumpyArray.__array_interface__['data'][0], ...)

【讨论】:

【参考方案2】:

在how to get the memory address of a numpy array for C中也使用__array_interface__,返回的整数是指向数组数据段的指针,没有内存地址:

数据(可选)

一个 2 元组,其第一个参数是一个整数(如果需要,是一个长整数)指向存储数组内容的数据区域。 该指针必须指向数据的第一个元素(换句话说 在这种情况下,任何偏移量都会被忽略)。中的第二个条目 tuple 是一个只读标志(true 表示数据区是只读的)。

这个属性也可以是一个暴露缓冲区接口的对象,用于共享数据。如果此键不存在(或 返回None),则内存共享将通过缓冲区完成 对象本身的接口。在这种情况下,偏移键可以是 用于指示缓冲区的开始。对对象的引用 暴露数组接口必须由新对象存储,如果 内存区域是要保护的。

默认:无

来源:https://docs.scipy.org/doc/numpy-1.13.0/reference/arrays.interface.html

你可以看到__array_interface__print x.__array_interface__[]返回的整个字典的内容

__array_struct__ 包含一个指向数组第一个元素的不同 C 指针,您可以在 C(++) 代码中访问它,例如在 http://blog.audio-tk.com/2008/11/04/exposing-an-array-interface-with-swig-for-a-cc-structure/ 中:

`

C 结构访问

这种数组接口方法允许更快地访问 仅使用一个属性查找和明确定义的 C 结构的数组。

__array_struct__

A :c:type: PyCObject 的 voidptr 成员包含一个指向已填充 PyArrayInterface 结构的指针。该结构的内存是 动态创建的,并且 PyCObject 也使用 适当的析构函数,因此该属性的检索器只需 将 Py_DECREF 应用于此属性返回的对象,当它是 完成的。此外,要么需要复制数据,要么需要参考 必须持有暴露此属性的对象以确保数据 没有被释放。暴露__array_struct__ 接口的对象必须 如果其他对象正在引用,也不会重新分配它们的内存 他们。

PyArrayInterface 结构在numpy/ndarrayobject.h 中定义为:

typedef struct 
  int two;              /* contains the integer 2 -- simple sanity check */
  int nd;               /* number of dimensions */
  char typekind;        /* kind in array --- character code of typestr */
  int itemsize;         /* size of each element */
  int flags;            /* flags indicating how the data should be interpreted */
                        /*   must set ARR_HAS_DESCR bit to validate descr */
  Py_intptr_t *shape;   /* A length-nd array of shape information */
  Py_intptr_t *strides; /* A length-nd array of stride information */
  void *data;          --------> /* A pointer to the first element of the array */ < ------
  PyObject *descr;      /* NULL or data-description (same as descr key
                                of __array_interface__) -- must set ARR_HAS_DESCR
                                flag or this will be ignored. */
 PyArrayInterface;

来源:https://docs.scipy.org/doc/numpy-1.13.0/reference/arrays.interface.html

【讨论】:

以上是关于从 numpy 数组获取指针以将图像发送到 C++的主要内容,如果未能解决你的问题,请参考以下文章

使用 ctypes 从 python 到 c++ 的数据传输

将 C++ 数组发送到 Python 并返回(使用 Numpy 扩展 C++)

如何使用 pinvoke 将图像从 c 或 c++ 发送到 C#

从 python 传递到 C++ 的数组中未映射的内存访问

PDO:获取类选项以将字段作为数组发送到构造函数

如何使用 ctypes 将数组从 C++ 函数返回到 Python