python - 从 boost::python::object 列表中获取单个元素,用于 python 例程

标签 python c++ boost boost-python

我有一个用于 Python 列表的 C++ boost python 对象(PyObject * 上的 boost 包装器),

  PyObject * pyList = func(...);
  boost::python::object listObj(handle<>(boost::python::borrowed(pyList)));

我可以通过对其执行操作来验证这确实是一个列表

boost::python::object np = import("numpy");
boost::python::np_difference = np.attr("diff");
np_difference(listObj);
for(int i=0; i<len(listObj); i++){                                                                                         
  double value = boost::python::extract<double>(listObj[i]);                                                                              
  cout << i << " " << value << endl;                                                                                       
} 

从 i-1 元素中减去第 i 个元素并创建一个新列表,然后提取其中的每个元素并将其打印到 C++ 中的 stdout。

我想做的是将这个 listObj 与我定义的打印函数一起使用

boost::python::object print = std.attr("print");    

但我只是希望它打印我指定的元素之一。在 python 中我只会写

print myList[0]

因为它只是一个Python列表。但当我尝试时

print(listObj[0]);

在 c++ 中使用 boost python 我得到

Error in Python: <type 'exceptions.TypeError'>: No to_python (by-value) converter found for C++ type: boost::python::api::proxy<boost::python::api::item_policies>.

那么如何从 python 列表对象访问单个元素并在 python 调用中使用它,就像上面的 print 方法(或任何其他接受字符串作为输入的 python 函数)一样,从 c++ 中调用?

最佳答案

boost::python::objectoperator[]返回 boost::python::proxy目的。虽然 proxy 类隐式转换为 boost::python::object ,API 中有许多区域需要显式转换。

proxy 显式构造 boost::python::object 应该可以解决转换异常:

print(boost::python::object(listObjString[0]));

这是一个完整的嵌入式 Python 示例,演示如何通过以下方式打印列表中的单个元素:

  • Python 内置 print 函数
  • Python/C API 中的PyObject_Print() 函数
  • 通过 __str__ 提取对象的字符串表示形式并使用 std::cout 打印
#include <boost/foreach.hpp>
#include <boost/python.hpp>
#include <boost/range/irange.hpp>

/// @brief Default flag to have PyObject_Print use the object's
///        __str__ method.  The python.h files only define the flag for
///        __repr__.
#define Py_PRINT_STR 0

int main()
{
  Py_Initialize();

  namespace python = boost::python;
  try
  {
    // Create and populate a Python list.
    // >>> list = [x for x in range(100, 103)]
    python::list list;    
    BOOST_FOREACH(int x, boost::irange(100, 103))
        list.append(x);

    // The proxy returned from a Boost.Python's operator[] provides a
    // user-defined conversion to a Boost.Python object.  In most cases,
    // explicitly invoking the conversion is required.

    // Print list[0] using the built-in function print.
    /// >>> getattr(__builtins__, 'print')(list[0])
    python::object print =
        python::import("__main__").attr("__builtins__").attr("print");
    print(python::object(list[0]));

    // Print list[1] using the Python/C API.
    // >>> import sys; sys.stdout.write(list[1].__str__())
    PyObject_Print(python::object(list[1]).ptr(), stdout, Py_PRINT_STR);
    std::cout << std::endl;

    // Print list[2] using the result of the object's __str__ method, and
    // extract a C++ string.
    std::cout << python::extract<std::string>(
                   python::object(list[2]).attr("__str__")())() << std::endl;

  }
  catch (python::error_already_set&)
  {
    PyErr_Print();
  }
}

输出:

100
101
102

关于python - 从 boost::python::object 列表中获取单个元素,用于 python 例程,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22674774/

相关文章:

Python:从 subprocess.call 捕获标准输出

python - 游戏的 flask 计数器

python - 通过 boto3 : ImproperlyConfigured 使用 Amazon S3 的 Django

c++ - 汇编中的内联 C++ 方法

python - 递归以找到 Python 中集合之间的共性

c++ - 如何从任意客户端查找 DHCP 租约信息?

c++ - 闭源库包括 boost 分发

boost ASIO : How to use limited buffer size with async_read_until

c++ - boost::asio::connect() 未找到

c++ - 空参数检查 C++