【问题标题】:How to extend a struct in SWIG with a static variable, with a custom getter and setter?如何使用静态变量和自定义 getter 和 setter 在 SWIG 中扩展结构?
【发布时间】:2017-03-14 10:54:43
【问题描述】:

我想包装一个结构的静态成员变量,以便在从 Python 读取或写入它时,在 C++ 端调用自定义 get/set 函数。以下适用于非静态变量。这是foo.h

#ifndef FOO_H
#define FOO_H

#include <iostream>

struct Foo
{
  static int bar() { std::cout << "Foo::bar()\n"; return 0; }
};

#endif

foo.i 如下所示:

%module foo
%{
  #include "foo.h"
%}

struct Foo
{
};

%extend Foo {
  int i;
}

%{
  int Foo_i_get(Foo* obj) {
    return Foo::bar();
  }
  void Foo_i_set(Foo* obj, int i) {}
%}

这种工作,在 Python 中我可以做到:

import foo
f = foo.Foo()
f.i

这会触发 Foo::bar() 被调用。我想要实现的是具有相同行为的以下内容:

import foo
foo.Foo.i

这不起作用,因为i 不是类属性。 我天真地尝试在.i 文件中更改以下内容:

%extend Foo {
  static int i;
}

这会在 SWIG 生成的以下包装器代码中产生编译错误:

SWIGINTERN PyObject *Swig_var_Foo_i_get(void) {
  PyObject *pyobj = 0;

  pyobj = SWIG_From_int((int)(Foo::i));
  return pyobj;
}

这是g++给出的错误信息:

foo_wrap.c: In function ‘PyObject* Swig_var_Foo_i_get()’:
foo_wrap.c:3208:31: error: ‘i’ is not a member of ‘Foo’
    pyobj = SWIG_From_int((int)(Foo::i));

所以显然这不是正确的方法。如何使用静态变量、自定义 setter 和 getter 扩展结构?

【问题讨论】:

  • 即使没有%extend SWIG 实际上也不会使类的静态成员可以通过foo.Foo.i 语法访问。我敢肯定,我们可以通过一些解决方法来做一些事情,但这不会是微不足道的。

标签: python c++ swig


【解决方案1】:

这可能有效:foo.i 如下所示:

%module foo
%{
  #include "foo.h"
%}

%include "foo.h"

%extend Foo {
  int get_i(){ return Foo::bar(); }
  %pythoncode %{
     i = property(get_i)
  %}
}

【讨论】:

  • 很久以前我需要这个,我不确定我最终如何以及是否找到了解决方案。我会记下并检查我是如何解决的;以及您的方法是否有效,感谢您迟来的回答!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-10-18
  • 1970-01-01
  • 2015-03-21
  • 2013-10-07
  • 1970-01-01
相关资源
最近更新 更多