2.面向对象-继承与多态

面向对象的继承与多态

1.继承

继承 : 一个类除了自身拥有的属性方法外,还获取了另一个类的属性方法
被继承的是父类(基类,超类)
继承的是子类(衍生类)    
继承种类:
    1.单继承
    2.多继承
python中所有类的父类是 object
1.1 单继承
# 单继承
"""
子类只能继承父类的公有成员,不能继承私有成员
在继承的环境中,对象的调取顺序:
    对象中->自己类中->父类中  都没有报错
"""
class Human():
    person="远古人类"
    __mimi="未解之谜"
    def drink(self):
        print("茹毛饮血")
    def __eat(self):
        print("吃的是烤肉")

class Man(Human):#继承父类
    def siyou(self):
        self.__eat()
    def drink(self):
        print("现代人喝饮料")

obj = Man()
# 1.子类可以使用父类的公有成员
print(obj.person) #远古人类

# 2.子类不能使用父类的私有成员
"""
obj.siyou() #报错 : 'Man' object has no attribute '_Man__eat'
"""
# 3.子类可以重写父类的公有成员
obj.drink() #现代人喝饮料
1.2 多继承
"""
多继承的弊端 : 
    会造成菱形继承这种情况,理不清调用顺序
super()对象会按照 mro 列表的顺序依次调用,解决菱形继承存在的问题
    类名.mro() 返回列表
    1.super 本身是一个类,super()是一个对象,用于掉用父类的绑定方法
	2.super 只应用在绑定方法中,默认自动传递self参数(前提: super所在作用域存在self)
	3.super作用 : 用于解决复杂的多继承调用顺序
	
经典类: 深度优先(python2.x)
新式类: 广度优先(python3.x)->横着遍历一级父类,二级父类...到最后父类

写多继承时,尽量避免造成不同类相同方法名的情况,提高代码质量 ,高内聚,低耦合
高内聚: 一个模块只完成一个任务,专一性高
低耦合: 模块与模块之间可以彼此独立不冲突,方便移植复用
"""

# 1.多继承
class Father():
    pty="抠脚大叔"
    def hobby(self):
        print("打球")
class Mother():
    pty="貌美如花"
    def hobby(self):
        print("刷韩剧")

class Son(Father,Mother): #继承父类
    pty="三好学生"
    def hobby(self):
        print("LOL")
    # 1.使用类调用类中成员
    def lei(self):
        print(Mother.pty)
        Father.hobby(self) #注意参数别忘写
    # 2.使用对象调用类中成员
    """对象调用顺序 : 对象成员->自己类成员->父类成员"""
    def duixiang(self):
        print(self.pty)
        self.hobby()
    # 3.使用super调用父类中成员
    """绑定方法 : 会自动把作用域self对象当成参数进行传递"""
    def sup(self):
        print(super().pty) #多个父类成员一样,找第一个继承的父类
        super().hobby() 

obj = Son()
obj.lei() #貌美如花,打球
obj.duixiang() #三好学生 LOL
obj.sup() #抠脚大叔,打球

# 2.菱形继承(钻石继承)
class Human():
    pty=4
    def feel(self):
        print("天热,脱1")
        print(self.pty)
        print("天冷,穿虎皮2")
class Man(Human):
    pty=3
    def feel(self):
        print("天热了,光膀子3")
        super().feel()
        print("天冷了,穿羽绒服4")
class Woman(Human):
    pty=2
    def feel(self):
        print("天热了,脱衣服5")
        super().feel()
        print("天冷了,穿羽绒服6")
class Son(Man,Woman):
    pty=1
    def feel(self):
        print("天热了,光屁股7")
        super().feel()
        print("天冷了,穿棉袄8")    

obj = Son()
obj.feel() 
"""
天热了,光屁股7
天热了,光膀子3
天热了,脱衣服5
天热,脱1
1
天冷,穿虎皮2
天冷了,穿羽绒服6
天冷了,穿羽绒服4
天冷了,穿棉袄8
"""
lst=Son.mro() #查看 super()对象调用顺序
print(lst)
"""
[
<class '__main__.Son'>,
<class '__main__.Man'>,
 <class '__main__.Woman'>,
 <class '__main__.Human'>,
 <class 'object'>
 ]
"""

# 3.相关函数
# 1.issubclass 判断谁是否是谁子类
"""
在判断子父关系时,只要在一条继承链上,就有继承关系
语法:
    1.issubclass(子类,父类) 满足返回True
    2.issubclass(子类,(父类1,父类2,....)) 只要满足一个就返回True
"""
res=issubclass(Son,Man) #True
res=issubclass(Son,Human) #True
print(res)

# 2.isinstance 判断对象是否是这个类(对象与类之间的关系)
"""
在判断对象类型时,只要在一条继承链上,就有继承关系
语法与issubclass一样
"""
class Car():
    pass
obj = Son()
print(isinstance(obj,Man)) #True
print(isinstance(obj,Human)) #True
print(isinstance(obj,Car)) #False
print(isinstance(obj,(Car,Human)))#True    

2.多态

# 1.多态
"""
多态: 不同的子类对象,调用相同的父类方法,产生不同的执行结果
特征: 继承,重写,针对于对象
作用: 在公司中,统一命名规则
"""
class Soldier(): #士兵
    def attack(self): #攻击  
        pass
    def back(self):  #撤退
        pass

class Army(Soldier): #陆军
    def attack(self):
        print("包子雷")
    def back(self):
        print("轻功水上漂")
class Navy(Soldier): #海军
    def attack(self):
        print("鱼叉")
    def back(self):
        print("水遁")
class AirForce(Soldier):
    def attack(self):
        print("导弹")
    def back(self):
        print("跳伞,落地成盒")

# 创建陆军士兵
objArmy=Army()
# 创建海军士兵
objNavy=Navy()
# 创建空军士兵
objAirForce=AirForce()

# 整装待发
lst=[objArmy,objNavy,objAirForce]
strvar="""
1.全军出击
2.全体撤退
3.陆军掩护其他兵种撤退
各就各位,将军请下令:
"""
num=input(strvar)
for i in lst:
    if num=="1":
        i.attack()
    elif num=="2":
        i.back()
    elif num=="3":
        if isinstance(i,Army):
            i.attack()
        else:
            i.back()
    else:
        print("听不清~~")
        break
原文地址:https://www.cnblogs.com/jia-shu/p/14146138.html