Digamos que tengo un escenario de herencia múltiple:
class A(object):
# code for A here
class B(object):
# code for B here
class C(A, B):
def __init__(self):
# What's the right code to write here to ensure
# A.__init__ and B.__init__ get called?
Hay dos enfoques típicos de la escritura C's __init__:
- (viejo estilo)
ParentClass.__init__(self) - (estilo más nuevo)
super(DerivedClass, self).__init__()
Sin embargo, en cualquier caso, si las clases principales ( Ay B) no siguen la misma convención, entonces el código no funcionará correctamente (algunos pueden perderse o recibir llamadas varias veces).
Entonces, ¿cuál es la forma correcta de nuevo? Es fácil decir "solo sea coherente, siga uno u otro", pero si es Ao Bes de una biblioteca de terceros, ¿entonces qué? ¿Existe un enfoque que pueda garantizar que se llame a todos los constructores de clases principales (y en el orden correcto, y solo una vez)?
Editar: para ver a qué me refiero, si lo hago:
class A(object):
def __init__(self):
print("Entering A")
super(A, self).__init__()
print("Leaving A")
class B(object):
def __init__(self):
print("Entering B")
super(B, self).__init__()
print("Leaving B")
class C(A, B):
def __init__(self):
print("Entering C")
A.__init__(self)
B.__init__(self)
print("Leaving C")
Entonces me sale:
Entering C
Entering A
Entering B
Leaving B
Leaving A
Entering B
Leaving B
Leaving C
Tenga en cuenta que Bel init se llama dos veces. Si lo hago:
class A(object):
def __init__(self):
print("Entering A")
print("Leaving A")
class B(object):
def __init__(self):
print("Entering B")
super(B, self).__init__()
print("Leaving B")
class C(A, B):
def __init__(self):
print("Entering C")
super(C, self).__init__()
print("Leaving C")
Entonces me sale:
Entering C
Entering A
Leaving A
Leaving C
Tenga en cuenta que Bnunca se llama a init. Por lo tanto, parece que a menos que sepa / controle los inicios de las clases que heredo de ( Ay B) no puedo tomar una decisión segura para la clase que estoy escribiendo ( C).