Python学习笔记__6.3章 继承和多态
# 这是学习廖雪峰老师python教程的学习笔记
1、概览
在OOP程序设计中,当我们定义一个class的时候,可以从某个现有的class继承,新的class称为子类(Subclass),而被继承的class称为基类、父类或超类(Base class、Super class)。
1.1、父类与子类的关系
子类可以继承父类的方法
子类的a方法 和 父类的a方法同名,则子类的a方法会 覆盖 父类的a方法
子类定义instance,既是子类的数据类型,又是父类的数据类型。反过来不行。【这叫多态】
定义一个类Animal,其中有方法 run()
class Animal(object):
def run(self):
print('Animal is running...')
定义一个子类Dog,其中也有方法 run()
class Dog(Animal):
def run(self):
print('Dog is running...')
验证方法的继承
>>> Dog().run() # Dog表示class,Dog()表示instance。且每次Dog() 创造的实例不同
Dog is running...
定义一个使用Anmial 数据类型的 函数
def run_twice(animal):
animal.run()
对比Animal() 和 Dog() 的不同
>>> run_twice(Animal())
Animal is running…
>>> run_twice(Dog())
Dog is running...
总结
对而言,run_twice()不做任何修改,任何依赖Animal作为参数的函数或者方法都可以不加修改地正常运行,原因就在于多态。
1.2、开闭原则
调用方只管调用,不管细节,而当我们新增一种Animal的子类时,只要确保run()方法编写正确,不用管原来的代码是如何调用的。
对扩展开放:允许新增Animal子类;
对修改封闭:不需要修改依赖Animal类型的run_twice()等函数。
2、静态语言 VS 动态语言
对于静态语言(例如Java)来说,如果需要传入Animal类型,则传入的对象必须是Animal类型或者它的子类,否则,将无法调用run()方法。
对于Python这样的动态语言来说,则不一定需要传入Animal类型。我们只需要保证传入的对象有一个run()方法就可以了。
class Timer(object):
def run(self):
print('Start...')
# 调用结果
>>> run_twice(Timer())
Start…
这就是动态语言的“鸭子类型”,它并不要求严格的继承体系,一个对象只要“看起来像鸭子,走起路来像鸭子”,那它就可以被看做是鸭子。只要你的 方法一样,不一定要传入真正符合数据类型的对象
转载于:https://blog.51cto.com/12758568/2116767