辅助函数中的 swig 宏 $descriptor

Posted

技术标签:

【中文标题】辅助函数中的 swig 宏 $descriptor【英文标题】:swig macro $descriptor within helper function 【发布时间】:2017-11-09 09:45:35 【问题描述】:

简介

我的典型 swig 接口文件类似如下:

% //COPY THIS BLOCK AS IS
    #include <headers.h>

    static CppClass* get_CppClass_from_swig_object(PyObject* obj)
    
        void* self_obj = nullptr;
        int ok = SWIG_Python_ConvertPtr(obj, &self_obj, SWIGTYPE_p_CppClass, 0);
        if(!SWIG_IsOK(ok))
        
            PyErr_SetString(PyExc_TypeError, "Object must be a CppClass");
            return nullptr;
        

        return reinterpret_cast<CppClass*>(self_obj);
    

    static CppClass convert_to_CppClass(PyObject* py_obj)
    
        CppClass* converted_ptr = get_CppClass_from_swig_object(py_obj);
        if(converted_ptr==nullptr)
            throw std::runtime_error("Python object is not a CppClass");

        return CppClass(*converted_ptr);
    
%


%typemap(in) std::vector<CppClass>& (std::vector<CppClass> temp) 
    try
        temp = SequenceConverter::to_vector<CppClass>($input, convert_to_CppClass);
        $1 = &temp;
    catch(std::exception& e)
        PyErr_SetString(PyExc_RuntimeError, e.what());
        SWIG_fail;
    


%typemap(typecheck, precedence=SWIG_TYPECHECK_CPPCLASS_VECTOR) std::vector<CppClass>& 
    $1 = 0;
    if(PyTuple_Check($input))
        $1 = 1;
    else if(PyList_Check($input))
        $1 = 1;



class CppClass

public:
    CppClass();
    CppClass(const CppClass& other);

    //other methods
;

但我想避免在get_CppClass_from_swig_object 中明确使用SWIGTYPE_p_CppClass

照原样,不可能像我想的那样使用$descriptor(CppClass) swig 宏,因为% ... % 块被复制为-is 而不是被swig 解释,因此$descriptor swig 宏会不被解释。另一方面,如果我删除% 并使用 ... 块,swig 将尝试包装整个get_CppClass_from_swig_objectconvert_to_CppClass 类,而不是简单地定义它们以便它们可以在类型映射中使用。

问题

如何更改我的文件结构并允许在转换助手中使用 $descriptor 宏?

TL;DR

%...% 块既不预处理也不被 swig 包装 ... 块都经过预处理和包装(但可以防止小块通过前面的 % 进行预处理) 如何进行 swig 预处理但不包装一段代码?

【问题讨论】:

【参考方案1】:

我认为没有办法使 %...% 的内容被预处理,但不被包装 - 对于预处理器所做的大部分工作,它依赖于实际实例化的类型映射来填充替换信息(尽管 @ 987654322@ 仍然可以工作,我过去一直希望它)。

我通常的解决方案是将 SWIG 类型信息作为参数传递给这样的函数,例如:

% //COPY THIS BLOCK AS IS
    #include <headers.h>

    static CppClass* get_CppClass_from_swig_object(PyObject* obj, swig_type_info *ty) 
    
        //... use ty instead of $descriptor here 

这意味着当您在类型映射中使用get_CppClass_from_swig_object 时,您只需使用$1_descriptor$descriptor 来获取第二个参数的正确值。

【讨论】:

以上是关于辅助函数中的 swig 宏 $descriptor的主要内容,如果未能解决你的问题,请参考以下文章

SWIG 不扩展嵌套宏“错误:输入中的语法错误 (3)”

带有模板类的 SWIG SHARED_PTR 宏

SWIG 和 windows 导出宏

SWIG 3 中文手册——8. 预处理

如何将复数从 python numpy 传递给 c(目前正在尝试使用 SWIG)

将派生类传递给采用 SWIG Python 中的基类的函数