python面向对象(多态)
# 1、什么是多态:同一事物有多种形态 class Animal: # 同一类事物:动物 def talk(self): pass class Cat(Animal): # 动物的形态之一:猫 def talk(self): print('喵喵喵') class Dog(Animal): # 动物的形态之二:狗 def talk(self): print('汪汪汪') class Pig(Animal): # 动物的形态之三:猪 def talk(self): print('哼哼哼') # 实例化得到三个对象 cat = Cat() dog = Dog() pig = Pig()
# 2、为何要有多态---》多态会带来什么样的特性,多态性 # 多态性指的是可以在不用考虑对象具体类型的情况下而直接使用对象, # 这就需要在设计时,把对象的使用方法统一成一种: # 例如cat、dog、pig都是动物,但凡是动物肯定有talk方法, # 于是我们可以不用考虑它们三者的具体是什么类型的动物,而直接使用 class Animal: # 同一类事物:动物 # 统一所有子类的方法 def talk(self): print('动物基本的发声频率', end=' ') class Cat(Animal): # 动物的形态之一:猫 def talk(self): super().talk() print('喵喵喵') class Dog(Animal): # 动物的形态之二:狗 def talk(self): super().talk() print('汪汪汪') class Pig(Animal): # 动物的形态之三:猪 def talk(self): super().talk() print('哼哼哼') cat = Cat() dog = Dog() pig = Pig() cat.talk() dog.talk() pig.talk() # 定义统一的接口,接收传入的动物对象 def func(animal): animal.talk() func(dog) # Python中一切皆对象,本身就支持多态性 # 我们可以在不考虑三者类型的情况下直接使用统计三个对象的长度 # str,list,tuple都是序列类型 s = str('hello') l = list([1, 2, 3]) t = tuple((4, 5, 6)) s.__len__() l.__len__() t.__len__() # Python内置了一个统一的接口 len(s) len(l) len(t)
# 3、通过在父类引入抽象类的概念来硬性限制子类必须有某些方法名 import abc # 指定metaclass属性将类设置为抽象类,抽象类本身只是用来约束子类的,不能被实例化 class Animal(metaclass=abc.ABCMeta): @abc.abstractmethod # 该装饰器限制子类必须定义有一个名为talk的方法 def talk(self): # 抽象方法中无需实现具体的功能 pass class Cat(Animal): # 但凡继承Animal的子类都必须遵循Animal规定的标准 def talk(self): pass cat = Cat() # 若子类中没有一个名为talk的方法则会抛出异常TypeError,无法实例化
# 4、python推荐的是鸭子类型 ''' 不依赖于继承,只需要制造出外观和行为相同对象,同样可以实现不考虑对象类型而使用对象, 这正是Python崇尚的“鸭子类型”(duck typing):“如果看起来像、叫声像而且走起路来像鸭子,那么它就是鸭子”。 比起继承的方式,鸭子类型在某种程度上实现了程序的松耦合度,如下 ''' # 二者看起来都像文件,因而就可以当文件一样去用,然而它们并没有直接的关系 class Txt: # Txt类有两个与文件类型同名的方法,即read和write def read(self): pass def write(self): pass class Disk: # Disk类也有两个与文件类型同名的方法:read和write def read(self): pass def write(self): pass
本质:对设计者而言,类的方法设置一样,都有talk方法,对使用者,就可以不考虑对象对应的类了,直接调用talk方法