自定义 SWIG 访问器函数或结构成员类型转换
Custom SWIG accessor functions or struct member type cast
我需要一些方法将 unit8_t 数组转换为 char 数组或 char * string 在 Python 端创建 Job 对象,并在从 C++ 端获取对象后打印它的字段。 SWIG 是否支持自定义访问器函数(即 get/set)或“魔术”arg 转换?
我尝试了 @ignore 功能来跳过 identifier 和 name 成员的处理,并且添加 %inline 访问函数但是 no result.
在Python中:
job = someFuncInCppCode()
print("Identifier: " + job.identifier)
调用 Python 打印时出错:
Execution error: can only concatenate str (not "SwigPyObject") to str
C++ 头文件
struct Job
{
static const int MaxIdentifierLength = 20;
static const int MaxNameLength = 40;
uint8_t identifier[MaxIdentifierLength];
uint8_t name[MaxNameLength];
uint32_t status;
};
SWIG 自动生成的代码:
SWIGINTERN PyObject *_wrap_Job_identifier_get(PyObject *SWIGUNUSEDPARM(self), PyObject *args) {
PyObject *resultobj = 0;
Job *arg1 = (Job *) 0 ;
void *argp1 = 0 ;
int res1 = 0 ;
PyObject *swig_obj[1] ;
uint8_t *result = 0 ;
if (!args) SWIG_fail;
swig_obj[0] = args;
res1 = SWIG_ConvertPtr(swig_obj[0], &argp1,SWIGTYPE_p_Xrite__Device_Cpp__Topaz__Job, 0 | 0 );
if (!SWIG_IsOK(res1)) {
SWIG_exception_fail(SWIG_ArgError(res1), "in method '" "Job_identifier_get" "', argument " "1"" of type '" "Job *""'");
}
arg1 = reinterpret_cast<Job * >(argp1);
result = (uint8_t *)(uint8_t *) ((arg1)->identifier);
resultobj = SWIG_NewPointerObj(SWIG_as_voidptr(result), SWIGTYPE_p_unsigned_char, 0 | 0 );
return resultobj;
fail:
return NULL;
}
一种方法是为该数组类型定义输出类型映射。参见 Typemaps for arrays in the SWIG documentation。示例:
test.i
%module test
%include <stdint.i>
// Convert uint8_t array assumed to be a null-terminated string.
%typemap(out) uint8_t[ANY] %{
$result = PyBytes_FromString(reinterpret_cast<char*>());
%}
%inline %{
#include <stdint.h>
struct Job
{
static const int MaxIdentifierLength = 20;
static const int MaxNameLength = 40;
uint8_t identifier[MaxIdentifierLength];
uint8_t name[MaxNameLength];
uint32_t status;
};
// test function
Job func() {
return {"hello","world",5};
}
%}
演示:
>>> import test
>>> j=test.func()
>>> j.name
b'world'
>>> j.identifier
b'hello'
>>> j.status
5
如果您希望数组中的每个字节都可见,请改用此类型映射:
%typemap(out) uint8_t[ANY] %{
$result = PyBytes_FromStringAndSize(reinterpret_cast<char*>(), _dim0);
%}
演示:
>>> import test
>>> j=test.func()
>>> j.identifier
b'hello\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00'
我需要一些方法将 unit8_t 数组转换为 char 数组或 char * string 在 Python 端创建 Job 对象,并在从 C++ 端获取对象后打印它的字段。 SWIG 是否支持自定义访问器函数(即 get/set)或“魔术”arg 转换?
我尝试了 @ignore 功能来跳过 identifier 和 name 成员的处理,并且添加 %inline 访问函数但是 no result.
在Python中:
job = someFuncInCppCode()
print("Identifier: " + job.identifier)
调用 Python 打印时出错:
Execution error: can only concatenate str (not "SwigPyObject") to str
C++ 头文件
struct Job
{
static const int MaxIdentifierLength = 20;
static const int MaxNameLength = 40;
uint8_t identifier[MaxIdentifierLength];
uint8_t name[MaxNameLength];
uint32_t status;
};
SWIG 自动生成的代码:
SWIGINTERN PyObject *_wrap_Job_identifier_get(PyObject *SWIGUNUSEDPARM(self), PyObject *args) {
PyObject *resultobj = 0;
Job *arg1 = (Job *) 0 ;
void *argp1 = 0 ;
int res1 = 0 ;
PyObject *swig_obj[1] ;
uint8_t *result = 0 ;
if (!args) SWIG_fail;
swig_obj[0] = args;
res1 = SWIG_ConvertPtr(swig_obj[0], &argp1,SWIGTYPE_p_Xrite__Device_Cpp__Topaz__Job, 0 | 0 );
if (!SWIG_IsOK(res1)) {
SWIG_exception_fail(SWIG_ArgError(res1), "in method '" "Job_identifier_get" "', argument " "1"" of type '" "Job *""'");
}
arg1 = reinterpret_cast<Job * >(argp1);
result = (uint8_t *)(uint8_t *) ((arg1)->identifier);
resultobj = SWIG_NewPointerObj(SWIG_as_voidptr(result), SWIGTYPE_p_unsigned_char, 0 | 0 );
return resultobj;
fail:
return NULL;
}
一种方法是为该数组类型定义输出类型映射。参见 Typemaps for arrays in the SWIG documentation。示例:
test.i
%module test
%include <stdint.i>
// Convert uint8_t array assumed to be a null-terminated string.
%typemap(out) uint8_t[ANY] %{
$result = PyBytes_FromString(reinterpret_cast<char*>());
%}
%inline %{
#include <stdint.h>
struct Job
{
static const int MaxIdentifierLength = 20;
static const int MaxNameLength = 40;
uint8_t identifier[MaxIdentifierLength];
uint8_t name[MaxNameLength];
uint32_t status;
};
// test function
Job func() {
return {"hello","world",5};
}
%}
演示:
>>> import test
>>> j=test.func()
>>> j.name
b'world'
>>> j.identifier
b'hello'
>>> j.status
5
如果您希望数组中的每个字节都可见,请改用此类型映射:
%typemap(out) uint8_t[ANY] %{
$result = PyBytes_FromStringAndSize(reinterpret_cast<char*>(), _dim0);
%}
演示:
>>> import test
>>> j=test.func()
>>> j.identifier
b'hello\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00'