[英]Why, when calling a function with self on the parent class, the child class is actually run in Python
我有两个具有以下定义的抽象类:
from abc import ABC, abstractmethod
class A(ABC):
def __init__(self, lst):
self.List = lst
@abstractmethod
def __enter__(self) -> 'Component':
return self
@abstractmethod
def __exit__(self, *exc):
pass
class B(ABC):
def __init__(self, lst):
self.List = lst
@abstractmethod
def run(self):
pass
现在,我有一个继承自这些类的类:
class C(A, B):
def __init__(self, lst):
A.__init__(self, lst)
B.__init__(self, lst)
def __enter__(self) -> 'C':
self.List.append('C.__enter__')
self.run()
return self
def __exit__(self, *exc):
self.List.append('C.__exit__')
def run(self):
self.List.append('C.run')
最后,我有一个继承自C
的类:
class D(C):
def __init__(self, lst):
super().__init__(lst)
def __enter__(self) -> 'D':
self.List.append('D.__enter__')
super().__enter__()
return self
def __exit__(self, *exc):
super().__exit__()
self.List.append('D.__exit__')
def run(self):
self.List.append('D.run')
super().run()
现在,我的代码如下所示:
my_d = D( ['start'] )
with my_d:
pass
print(my_d)
根据我对super()
工作原理的了解,这应该产生以下内容:
[ start,
D.__enter__,
C.__enter__,
C.run,
C.__exit__,
D.__exit__ ]
但是实际发生的是:
[ start,
D.__enter__,
C.__enter__,
D.run,
C.run,
C.__exit__,
D.__exit__ ]
我无处可显式调用D.run
,但D.run
调用D.run
。
除非我在D中调用super().__enter__
,否则self
以某种方式认为它实际上在C
时仍在D
,这对我来说真的没有意义。 有人可以启发我吗?
在调用C.run
时调用D.run
:
class D(C):
def run(self):
self.List.append('D.run')
super().run() # this will add 'C.run' to self.List
与__exit__
和__enter__
相同。
D.run
从链称为D.__enter__
- > C.__enter__
现在调用self.run()
并作为self
具有type
D
这将调用D.run
- > C.run
)。
self
不认为这是“ D
内部”; self
是类型D
如果要获得所需的输出,则不能覆盖在D
run
; 这样,只会C.run
。
def run()
在d覆盖def run()
所以C.当你调用run()
在C.__enter__
,它实际上调用D.run()
当D.run()
被称为super().run()
调用C.run()
第一次学习python类继承时,这同样让我感到困惑,但这就是它的工作方式。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.