python - 如何在 C(++) 中(反)序列化 PyObject*?

标签 python c serialization python-c-api

我目前正在使用 C(++) 开发多线程 python 模块。我快完成了,但我需要做的最后一件事是找到一种绕过 GIL 的方法,以便线程之间的通信成为可能。

为此,我希望尝试以下伪代码:

// Called from Python
Pyobject* send_data(data, procid) {
    // Change the Python object to byte data and 
    // store it outside of python's memory management.
    serialized = serialize(data);

    // Send the byte data to desired processor
    // (Stored in a queue on that processor)
    send(serialize, procid);
}

// Called from python
Pyobject* receive_data() {
    // Grab data from queue
    serialized = grab_data();

    // De-serialize data
    data = de_serialize(serialized);

    return data;
}

之所以希望在发送之前序列化数据,是因为必须知道发送数据的内存大小。由于 sizeof(PyObject*) = 8,这是我确保大小始终正确的尝试。

现在,我找到了一种使用 pickle 在 python 中序列化数据的方法,但不知道如何以计算上可接受的方式将其传输到 C。 (因此,无需调用启动 python 实例的函数,导入正确的库并将 pickle 函数作为可调用函数发送到 C。)

任何有助于实现这一目标的帮助将不胜感激!

当然,如果您知道如何从 PyObject 获取准确的大小数据并知道如何将它们克隆到 C,那就太好了! ^_^'

最佳答案

当您使用两种不同的语言处理序列化数据时,与语言无关的序列化标准怎么样?这意味着模式优先的方法。

这是避免将每个数据结构定义编写两次的最佳方法,一次在 C 中,一次在 Python 中,如果您有复杂的数据结构,则特别有用。

对于 Python 和 C 来说,选择都有点少。有 Google Protocol Buffers hereC version here 、 Apache 阿夫罗 here也可能会工作,ASN.1(如果你感觉勇敢 overviewrecommended referencePlaygroundCommercialCommercial ,并在 GitHub 上查看一些免费的)。

所有这些的一般方法是从模式生成 Python、C(或 C#、Java、C++)源代码。源代码定义数据结构以及将其序列化/反序列化为通用线格式所需的函数/方法。这些函数的输出/输入是一个字节数组,因此在 C 端使用时它们的内容不会涉及 GIL。

有了可以正常工作的成熟工具,这是一种非常自由的数据交换方式;您可以根据需要在系统中混合使用语言。 ASN.1 尤其非常好,因为它的约束系统允许人们非常具体地了解什么是有效数据、什么不是有效数据。强大的接口(interface)! Google Protocol Buffers 几乎是完美的(因为它是免费的并且几乎可以完成所有操作),但没有任何限制。

如果您只有简单的数据结构,那么将每个结构定义编写两次的开销可能不会那么糟糕。因此,任何像样的 C Pickle 库都可以做得很好,只要它们不只是从 Pickle 构建 Python 对象。

关于python - 如何在 C(++) 中(反)序列化 PyObject*?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/53889155/

相关文章:

python - Python Properties类的Json序列化

python - 从字符串中删除括号和特殊字符并转换列表(值以逗号分隔)

python - 通常只切片列表/元组的一个元素?

python - 循环和计数 w/find

c - 在不使用临时变量的情况下交换 C 中两个不同数组的元素

c - 使用 malloc 对 double 动态数组进行合并排序,内存问题

c - 修改后的lua : Lua_close freezes in pthread

python - 多个参数 psycopg2 where 子句 - 语法错误

c# - 为什么反序列化不起作用?

java - 如何使用 Jackson 序列化基于 java.util.Map 的类