c++ - 如何处理我的 C++ __getitem__ 函数中的切片(由 SWIG 使用)

标签 c++ python swig

我正在为 C++ 类开发 Python 绑定(bind),该类扩展了 std::vector实例化。为了让 Python 下标运算符适用于此类,我添加了 __getitem__函数如下(我删除了不相关的代码和错误处理):

class Column;

typedef vector<Column*> MetaDataBase;

class MetaData : public MetaDataBase {
public:

#ifdef SWIGPYTHON
Column* __getitem__(int i) { return (*this)[i]; }
#endif
};

上面的代码在 Python 中可以正常访问单个元素,但不适用于切片。

好的,所以我知道我需要将函数参数的类型更改为 PyObject *并使用PySlice_Check查看该函数是否应该返回 PyList .

这很好,没问题。但因为我要返回PyList有时从函数来看, __getitem__ 的类型返回值必须是 PyObject*同样,我不能依赖 SWIG 将我的 C++ 类型 ( Column * ) 转换为包装类。另外,在创建切片时,我需要“手动”转换 Column*PyObject*在将其插入 PyList 之前。

我该怎么做?

最佳答案

我认为 std::vector 有一个更简单的解决方案使用 SWIG+Python。 SWIG 的 Python 代码生成已经支持很好地包装一些 STL 容器。

如果您添加到模块界面的开头:

%include "pyabc.i"
%include "std_vector.i" // Assuming you don't already

在某个地方,如果你还没有这样做的话:

%template(MetaDataBase) std::vector<Column*>;

那么这将导致包裹 std::vector满足Python的要求MutableSequence 。 (我认为这应该足以实现您在 Python 端寻找的目标,您可能还需要使用 -extranative 调用 SWIG)。

还可能值得注意 - 对于您当前的__getitem__您可以使用以下内容在 SWIG 接口(interface)文件中声明和定义它:

%extend MetaData {
   Column* __getitem__(int i) { return (*self)[i]; }
};

这允许您在不使用 SWIG+Python 特定代码“污染”您的“正常”头文件的情况下执行此操作。

关于c++ - 如何处理我的 C++ __getitem__ 函数中的切片(由 SWIG 使用),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8218314/

相关文章:

python - 是否有适用于 Python 的 Term::ANSIScreen 等效项?

Python 从字符串创建模块并运行该模块

c++ - swig 使用变量扩展模板类

java - 为什么它甚至可以编译? - 使用 swig 生成的类从 java 编译和运行 native 方法

c++ - 在带有 Visual Studio 的 Windows 上使用 swig -go

c# - wcf:调试 native c++ dll?

c++ - C++ 绿色线程的堆栈分配

c++ - 提高可读性的 C++ 结构,计算结果为非宏

c++ - shgetvalue 运行时错误

python - 将 pd 数据框填写到现有的 excel 表中(使用 openpyxl v2.3.2)