我一直在阅读关于python中的组合的文章,并且在这里跟随了一些关于stackoverlow的文章和答案之后,我想我能够得到什么是和如何实现。但是我找不到答案的一个问题是,为什么是作文?(与继承福利相比)。下面是我从here获得的一个例子
class Salary:
def __init__(self,pay):
self.pay=pay
def get_total(self):
return (self.pay*12)
class Employee:
def __init__(self,pay,bonus):
self.pay=pay
self.bonus=bonus
self.obj_salary=Salary(self.pay)
def annual_salary(self):
return "Total: " + str(self.obj_salary.get_total()+self.bonus)
obj_emp=Employee(100,10)
print (obj_emp.annual_salary())
我想用一个实际的例子来理解,通过分离两个相关的类(和确切的好处是什么?),它将从中受益。
发布于 2017-06-21 15:42:24
使用示例的扩展版本
class Salary:
def __init__(self,pay):
self.pay=pay
def get_total(self):
return (self.pay*12)
def increase(self):
self.pay *= 1.1
class Employee:
def __init__(self,pay,bonus):
self.pay=pay
self.bonus=bonus
self.obj_salary=Salary(self.pay)
def annual_salary(self):
return "Total: " + str(self.obj_salary.get_total()+self.bonus)
obj_emp=Employee(100,10)
print (obj_emp.annual_salary())
调用employee.salary.increase比employee.increase更有意义
另外,如果您需要多个对象,怎么办?你是继承了其中的一个,还是所有的都会导致名字可能的冲突?
class Game:
def __init__(self):
self.screens = [LoadingScreen, MapScreen]
self.player = Player()
self.display = Display()
self.stats = Stats(self.display)
self.screenIndex = self.player.getScreen()
self.currentScreen = self.screens[self.screenIndex]()
self.run()
*编辑*在看完这个之后
but on looking it up again i find that increase could be renamed to increaseSalary so employee.increaseSalary() would make sense right?
只需将加薪移到employee类,但如果您有Manager类或Boss类,则需要对每个类重复相同的代码。
class Employee:
def __init__(self,pay,bonus):
self.pay=pay
self.bonus=bonus
def annual_salary(self):
return "Total: " + str(self.obj_salary.get_total()+self.bonus)
def increase_salary(self):
self.pay *= 1.1
class Manager:
def __init__(self,pay,bonus):
self.pay=pay
self.bonus=bonus
def annual_salary(self):
return "Total: " + str(self.obj_salary.get_total()+self.bonus)
def increase_salary(self):
self.pay *= 1.1
class Boss:
def __init__(self,pay,bonus):
self.pay=pay
self.bonus=bonus
def annual_salary(self):
return "Total: " + str(self.obj_salary.get_total()+self.bonus)
def increase_salary(self):
self.pay *= 1.1
或只有一次
class Salary:
def __init__(self,pay):
self.pay=pay
def get_total(self):
return (self.pay*12)
def increase(self, addition):
self.pay *= addition
您还可以使用类方法来查找平均值、最大值、最小值等更简单的方法。
发布于 2017-06-21 15:55:24
好吧,我会试一试,尽管我是个菜鸟。另外,我可能遗漏了一些要点,但我喜欢这样想,不管是谁,答案是:
因为它提供了很大的灵活性,并允许您将不一定具有父/子关系的对象“组合”在一起(在经典的OOP中称为IS-A类型继承)。
例如,假设您有一个rifle
类。您希望向其添加(或撰写) attachments
。
你怎么能继承遗产呢?不会很灵活的。
因此,您可以做的是将附件定义为有自己的类,比如sight
和muzzle break
类,然后将这些附件类的实例声明为rifle
类中的字段,现在您可以访问sight
和muzzle break
中定义的方法,就像继承时子类可以访问它的超类方法一样。
无论如何,为了继续,您可以从这个示例中看到现在创建各种武器类(如howitzer
)是多么容易,如果操作得当,您可以在howitzer
中声明sight
和muzzle break
的实例。
注意,我们创建的关系层次结构是完全平坦的。
要使用继承来完成所有这些工作,您需要定义一个基类,比如weapon
,它使用在sight
和muzzle break
中定义的相同方法。然后,将扩展到rifle
和howitzer
的子类进行缓存。
现在假设您不希望rifle
拥有一个sight
,而是一个scope
。为了达到这个目的,你必须在你的基类中经历所有这些圈套和恶作剧。
对于组合,您只需创建一个新的类scope
(实际上可以继承sight
),从rifle
中删除sight
实例并插入scope
的字段实例。请注意,没有对howitzer
进行任何更改。
尽管如此,我仍然认为继承是一个有用的工具,可以在适当的情况下使用,就像构图一样。
https://stackoverflow.com/questions/44680490
复制相似问题