Dato che Python consente l'ereditarietà multipla, che aspetto ha l'ereditarietà idiomatica in Python?
Nelle lingue con ereditarietà singola, come Java, l'ereditarietà verrebbe utilizzata quando si potrebbe dire che un oggetto "è-a" di un altro oggetto e si desidera condividere il codice tra gli oggetti (dall'oggetto padre all'oggetto figlio ). Ad esempio, potresti dire che Dog
è un Animal
:
public class Animal {...}
public class Dog extends Animal {...}
Ma poiché Python supporta l'ereditarietà multipla, possiamo creare un oggetto componendo molti altri oggetti insieme. Considera l'esempio seguente:
class UserService(object):
def validate_credentials(self, username, password):
# validate the user credentials are correct
pass
class LoggingService(object):
def log_error(self, error):
# log an error
pass
class User(UserService, LoggingService):
def __init__(self, username, password):
self.username = username
self.password = password
def authenticate(self):
if not super().validate_credentials(self.username, self.password):
super().log_error('Invalid credentials supplied')
return False
return True
È un uso accettabile o buono dell'ereditarietà multipla in Python? Invece di dire che l'ereditarietà è quando un oggetto "è-a" di un altro oggetto, creiamo un modello User
composto da UserService
e LoggingService
.
Tutta la logica per le operazioni di database o di rete può essere mantenuta separata dal modello User
inserendole nell'oggetto UserService
e mantenendo tutta la logica per la registrazione in LoggingService
.
Vedo che alcuni problemi con questo approccio sono:
- Questo crea un oggetto divino? Dal momento che
User
eredita da, o è composto da,UserService
eLoggingService
sta davvero seguendo il principio della responsabilità singola? - Per accedere ai metodi su un oggetto principale / next-in-line (ad esempio,
UserService.validate_credentials
dobbiamo usaresuper
. Ciò rende un po 'più difficile vedere quale oggetto gestirà questo metodo e non è chiaro come, diciamo, istanziandoUserService
e facendo qualcosa comeself.user_service.validate_credentials
Quale sarebbe il modo Python per implementare il codice sopra?