Учитывая, что Python допускает множественное наследование, как выглядит идиоматическое наследование в Python?
В языках с единичным наследованием, таких как Java, наследование будет использоваться, когда вы можете сказать, что один объект «a-a» другого объекта и вы хотите разделить код между объектами (от родительского объекта до дочернего объекта). Например, вы можете сказать, что Dog
это Animal
:
public class Animal {...}
public class Dog extends Animal {...}
Но поскольку Python поддерживает множественное наследование, мы можем создать объект, составив множество других объектов вместе. Рассмотрим пример ниже:
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
Это приемлемое или хорошее использование множественного наследования в Python? Вместо того чтобы говорить, что наследование - это когда один объект «является-а» другого объекта, мы создаем User
модель, состоящую из UserService
и LoggingService
.
Вся логика для баз данных или сетевых операций может храниться отдельно от User
модели, помещая их в UserService
объект и сохраняя всю логику для входа в систему LoggingService
.
Я вижу некоторые проблемы с этим подходом:
- Создает ли это объект Бога? Поскольку
User
наследует или состоит из,UserService
иLoggingService
действительно ли он следует принципу единой ответственности? - Для того, чтобы получить доступ к методам родительского / следующего в строке объекта (например,
UserService.validate_credentials
мы должны использоватьsuper
. Это немного затрудняет просмотр объекта, который будет обрабатывать этот метод, и не так ясно, как, скажем, , создаваяUserService
и делая что-то вродеself.user_service.validate_credentials
Что бы Pythonic способ реализовать вышеупомянутый код?