Я хочу использовать два экземпляра базового класса из одного производного класса. Я не уверен, что следующий код технически правильный или есть лучший способ. Могут ли эти два экземпляра смешиваться в любой ситуации?
Базовый класс A предназначен для выполнения общей задачи: «changevar», который изменяет переменную «var» на «dv». Производный класс B использует этот метод, но с двумя переменными «var1», «var2», чтобы изменить его на «dv1» и «dv2» соответственно. Затем класс B выполняет «операцию» над измененными переменными «var1» и «var2» и возвращает результат (в данном случае умножение).
test.py:
class A:
def __init__(self, var):
self.var = var
def changevar(self, dv):
self.var = self.var + dv
def getvar(self):
return self.var
class B(A):
def __init__(self, var1, var2):
self.var1 = var1
self.var2 = var2
A.__init__(self, var1)
self.inst1 = A(self.var)
A.__init__(self, var2)
self.inst2 = A(self.var)
def operation(self):
dv1 = 2
dv2 = -2
self.inst1.changevar(dv1)
self.inst2.changevar(dv2)
self.var1 = self.inst1.getvar()
self.var2 = self.inst2.getvar()
return self.var1, self.var2, self.var1 * self.var2
def main():
test = B(10, 10)
v1, v2, v3 = test.operation()
print (v1, v2, v3)
return
if __name__ == "__main__":
main()```
>>>python3 test.py
>>>12 8 96
В вашем коде вы на самом деле не используете наследование.
Когда вы выполняете self.inst1 = A(self.var)
, вы создаете совершенно новый экземпляр A, который отличается от того, который является базовым для вашего B, и назначаете его полю.
Хорошие новости: вам не нужно наследование в вашем случае. то, что вам нужно (и де-факто), это композиция - наличие полей типа A в вашем типе B.
Просто уберите A как базу вообще из B, и используйте внутренние поля этого типа, результат будет тот же:
class A:
def __init__(self, var):
self.var = var
def changevar(self, dv):
self.var = self.var + dv
def getvar(self):
return self.var
class B:
def __init__(self, var1, var2):
self.inst1 = A(var1)
self.inst2 = A(var2)
def operation(self):
dv1 = 2
dv2 = -2
self.inst1.changevar(dv1)
self.inst2.changevar(dv2)
var1 = self.inst1.getvar()
var2 = self.inst2.getvar()
return var1, var2, var1 * var2
def main():
test = B(10, 10)
v1, v2, v3 = test.operation()
print (v1, v2, v3)
return
if __name__ == "__main__":
main()
Наследование следует использовать, когда вы хотите использовать экземпляры типа B, как если бы они были типа A (например, вызывать методы A для экземпляров типа B). Обычно мы говорим, что B должен наследовать от A, ib B «является» A - например. Собака — это Животное, Квадрат — это Форма. Композиция больше связана с отношениями «имеет», как у автомобиля есть радио.
Надеюсь, я ясно дал понять, что немного сложно понять это рассуждение с бессмысленными именами классов, такими как A и B :)
Большое спасибо за ответ. Это решает мою проблему на данный момент и дополнительно знакомит с концепцией композиции.