- html - 出于某种原因,IE8 对我的 Sass 文件中继承的 html5 CSS 不友好?
- JMeter 在响应断言中使用 span 标签的问题
- html - 在 :hover and :active? 上具有不同效果的 CSS 动画
- html - 相对于居中的 html 内容固定的 CSS 重复背景?
我有一个A类。
我有另一个 B 类。 B 类的实例的功能应该与 A 类完全一样,除了一个警告:我想要另一个名为 special_method(self, args, kwargs)
的可用函数。
所以以下应该工作:
instance_A = classA(args, kwargs)
instance_B = classB(instance_A)
method_result = instance_B.special_method(args, kwargs)
我如何编写 B 类来实现这一点?
special_method
到 C、D、E、F 类...等。
最佳答案
因此,您正在描述代理对象。在 Python 中为非特殊方法执行此操作是微不足道的,您可以使用 __getattr__
In [1]: class A:
...: def foo(self):
...: return "A"
...:
In [2]: class B:
...: def __init__(self, instance):
...: self._instance = instance
...: def special_method(self, *args, **kwargs):
...: # do something special
...: return 42
...: def __getattr__(self, name):
...: return getattr(self._instance, name)
...:
In [3]: a = A()
In [4]: b = B(a)
In [5]: b.foo()
Out[5]: 'A'
In [6]: b.special_method()
Out[6]: 42
但是,这里有一个警告:这不适用于特殊方法,因为特殊方法会跳过属性解析的这一部分并直接在类
__dict__
上查找。 .
def special_method(self, *args, **kwargs):
# do something special
return 42
for klass in [A, C, D, E, F]:
klass.special_method = special_method
当然,这会影响这些类的所有实例(因为您只是动态地向类添加方法)。
def special_method(self, *args, **kwargs):
# do something special
return 42
_SPECIAL_MEMO = {}
def dynamic_mixin(klass, *init_args, **init_kwargs):
if klass not in _SPECIAL_MEMO:
child = type(f"{klass.__name__}Special", (klass,), {"special_method":special_method})
_SPECIAL_MEMO[klass] = child
return _SPECIAL_MEMO[klass](*init_args, **init_kwargs)
class Foo:
def __init__(self, foo):
self.foo = foo
def __len__(self):
return 88
def bar(self):
return self.foo*2
special_foo = dynamic_mixin(Foo, 10)
print("calling len", len(special_foo))
print("calling bar", special_foo.bar())
print("calling special method", special_foo.special_method())
上面的脚本打印:
calling len 88
calling bar 20
calling special method 42
关于python - 使用新方法动态包装任意类,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/67261104/
如果有人能为我分解它,让我能理解它,我会非常感激。我知道它用于通过 apply 方法创建新对象。 Function.prototype.new = function () { var args
新版本的HADOOP中有一个方法。http://hadoop.apache.org/docs/current/api/org/apache/hadoop/fs/FileSystem.html#conc
根据支持库变更日志和 Fragment 类文档 ( https://developer.android.com/reference/android/support/v4/app/Fragment.ht
根据支持库更改日志和 Fragment 类文档 (https://developer.android.com/reference/android/support/v4/app/Fragment.htm
执行Async BigJob() 的无限运行任务的正确方法是什么?并且可以根据要求停止 提示:我正在尝试学习 [一种] 新方法来更新我现有的策略。 我有一个简单的程序(测试程序),它有一个开始 和停止
我将解释我的想法:我使用 python 作为谷歌应用程序引擎 + js + css 主项目将存储在 src 文件夹下,如下所示:\src \app <--- 这里是 gae 的所有 python 应用
我是一名优秀的程序员,十分优秀!