扩展 SWIG 内置类
SWIG 的 -builtin 选项的优点是速度更快,并且可以避免多重继承的错误。
挫折是我无法在生成的类或任何子类上设置任何属性:
-我可以通过子类化 python 内置类型(如列表)而轻松地扩展它:
class Thing(list):
pass
Thing.myattr = 'anything' # No problem
-但是,在 SWIG 内置类型上使用相同的方法,会发生以下情况:
class Thing(SWIGBuiltinClass):
pass
Thing.myattr = 'anything'
AttributeError: type object 'Thing' has no attribute 'myattr'
我如何解决这个问题?
The -builtin option of SWIG has the advantage of being faster, and of being exempt of a bug with multiple inheritance.
The setback is I can't set any attribute on the generated classes or any subclass :
-I can extend a python builtin type like list, without hassle, by subclassing it :
class Thing(list):
pass
Thing.myattr = 'anything' # No problem
-However using the same approach on a SWIG builtin type, the following happens :
class Thing(SWIGBuiltinClass):
pass
Thing.myattr = 'anything'
AttributeError: type object 'Thing' has no attribute 'myattr'
How could I work around this problem ?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
我很偶然地找到了一个解决方案。我正在尝试元类,认为我可以设法覆盖子类中内置类型的 setattr 和 getattr 函数。
这样做我发现内置函数已经有一个元类(SwigPyObjectType),所以我的元类必须继承它。
就是这样。仅此一点就解决了问题。如果有人能解释原因,我会很高兴:
I found a solution quite by accident. I was experimenting with metaclasses, thinking I could manage to override the setattr and getattr functions of the builtin type in the subclass.
Doing this I discovered the builtins already have a metaclass (SwigPyObjectType), so my metaclass had to inherit it.
And that's it. This alone solved the problem. I would be glad if someone could explain why :
问题来自于 swig 如何实现“-builtin”中的类,就像内置类一样(因此得名)。
内置类不可扩展 - 尝试添加或修改“str”的成员,并且 python 不会让您修改属性字典。
我确实有一个已经使用多年的解决方案。
我不确定我是否可以推荐它,因为:
但是..我喜欢它在解决我们想要的一些晦涩功能方面的效果调试。
最初的想法不是我的,我是从以下地方得到的:
https://gist.github.com/mahmoudimus/295200 作者:Mahmoud Abdelkader
基本思想是将 swig 创建的类型对象中的 const 字典作为非常量字典进行访问,并添加/覆盖任何所需的方法。
仅供参考,类的运行时修改技术称为 Monkeypatching,请参阅 https://en.wikipedia.org/ wiki/Monkey_patch
首先 - 这是“monkeypatch.py”:
这是一个使用 Monkeypatch 的人为示例:
我在模块“mystuff”中有一个类“myclass”,包裹着swig -python -builtin
我想添加一个额外的运行时方法“namelen”,它返回 myclass.getName() 返回的名称的长度
请注意,这也可以用于扩展或覆盖内置 python 类上的方法,如所示在 Monkeypatch.py 的测试中:它向内置 str 类添加了一个方法“foo”,该方法返回带有随机大/小写字母的原始字符串的副本,
我可能会替换:
with
以避免额外的全局变量
The problem comes from how swig implemented the classes in "-builtin" to be just like builtin classes (hence the name).
builtin classes are not extensible - try to add or modify a member of "str" and python won't let you modify the attribute dictionary.
I do have a solution I've been using for several years.
I'm not sure I can recommend it because:
But.. I love how well it works to solve some obscure features we wanted for debugging.
The original idea is not mine, I got it from:
https://gist.github.com/mahmoudimus/295200 by Mahmoud Abdelkader
The basic idea is to access the const dictionary in the swig-created type object as a non-const dictionary and add/override any desired methods.
FYI, the technique of runtime modification of classes is called monkeypatching, see https://en.wikipedia.org/wiki/Monkey_patch
First - here's "monkeypatch.py":
Here's a contrived example using monkeypatch:
I have a class "myclass" in module "mystuff" wrapped with swig -python -builtin
I want to add an extra runtime method "namelen" that returns the length of the name returned by myclass.getName()
Note that this can also be used to extend or override methods on builtin python classes, as is demonstrated in the test in monkeypatch.py: it adds a method "foo" to the builtin str class that returns a copy of the original string with random upper/lower case letters
I would probably replace:
with
to avoid extra global variables