继承及其相关

时间:2019-02-19
本文章向大家介绍继承及其相关,主要包括继承及其相关使用实例、应用技巧、基本知识点总结和需要注意事项,具有一定的参考价值,需要的朋友可以参考一下。

OOP的三大特征(优势)
1.封装
2.继承
3.多态

继承
  继承是两个对象之间产生的一种关系
  a继承b 例如:儿子与父亲
  在OOP的程序中继承是描述类与类之间的一种关系

  继承的好处:生活中你继承你爹的财产 就可以直接使用这些财产
              程序中 一个类a 继承另一个b a就可以直接使用b类中的
              属性和方法
  具体的说:继承极大的提高了代码的重用性
  名词解释:a继承b  a称之为子类(派生类) b称之为父类(基类)
  注意:继承描述的是 什么是什么的关系  人是动物
    在使用继承时  要信分析 类与类之间的关系 不应该违反显示生活中的原则

 

class Teacher:
    school = "xxxx"
    def __init__(self,name,gender,age):
        self.name = name
        self.gender = gender
        self.age = age

    def teaching(self):
        print("%s is teaching" % self.name)

class Student(Teacher):

def studying(self):
    print("%s is studying" % self.name)

t1 = Teacher("xx","man",17)
t1.teaching()

stu1 = Student("xxx","man",56)
stu1.studying()

 

 

在使用继承的时候 一定是先抽象 在继承
抽象
抽取一堆类共同拥有的内容 形成一个新的抽象概念(类 也称之为公共基类) 这个过程就叫做抽象
例如 猪悟能  小猪佩奇  麦兜 都属于猪
     王健临  码云   刘强西 都属于人类
     猪和人都属于动物类 这就是抽象
注意:很多情况下 抽象得到的新的类型与业务是不相关的 仅仅是因为代码需要

class XxPerson:
    school = "xxxx"

    def __init__(self, name, gender, age):
        self.name = name
        self.gender = gender
        self.age = age

    def say_hi(self):
        print("hello my is %s" % self.name)

class Teacher(XxPerson):
    def teaching(self):
        print("%s is teaching" % self.name)

class Student(XxPerson):
    def studying(self):
        print("%s is studying" % self.name)

t1 = Teacher("xx","man",17)
t1.teaching()
t1.say_hi()

stu1 = Student("xxx","man",58)
stu1.studying()
stu1.say_hi()

 

没有继承关系的时候
    对象 -> 类中
存在继承关系后
    对象 -> 自身的类中 -> 父类 父类的父类。。。。。object
object:
    object 是所有类的根类  所有类都直接或间接的继承自object
    在定义类的时候 如果你没有手动继承任何类 默认继承object
    object 中包含所有对象通用的方法

新式类与经典类:
    新式类 只要是继承自object都叫新式类  在python3中所有类都是新式类
    python2 中不会自动继承object   需要手动继承object才能变成一个新式类
    新式类和经典类的区别在与继承关系中的属性的查找顺序不同

 

一切皆对象:

li2 = list((1,2))
print(li2)

li2.append(3)
print(li2)

list.append(li2,100)
print(li2)

 

可以继承一个系统已有的类  来扩展新功能
需求:给list扩展类型限制的功能  只允许存储整形数据

class MyList(list):
    def append(self, object):
        print("append run")
        if type(object) == int: # 判断类型
            list.append(self,object) # 调用原始的添加元素方法
        else:
            print("元素必须是整形")

li = MyList()
li.append(100)
li.append("abcd")
print(li)

 

 

派生与覆盖:

派生
    当一个类继承另一个类 并存在与父类不同的内容时 就称之为派生类
    通常情况下一个子类就是一个派生类

覆盖
    在继承关系中 子类可以出现与父类完全相同的方法  根据查找顺序 会优先使用
    子类中的方法  这中情况就称之为覆盖

 

class Person:

    def __init__(self,name,sex,age):
        self.name = name
        self.sex = sex
        self.age = age

    def say_hi(self):
        print(self.name)

class Student(Person):

    # 覆盖父类中的say_hi方法
    def say_hi(self):
        print("i am a student name is %s" % self.name)

stu1 = Student("牛大儿子","man",100)
stu1.say_hi()

 

 

很多情况下我们需要在子类中来访问父类中的内容
就可以通过super().要访问的名字

class Person:
    test = "12345"
    def __init__(self, name, sex, age):
        self.name = name
        self.sex = sex
        self.age = age

    def say_hi(self):
        print(self.name,self.sex,self.age)

class Student(Person):
    def __init__(self,name,sex,age,number):
        # self.name = name
        # self.sex = sex
        # self.age = age
        # Person.__init__(self,name,sex,age) # 子类重用父类方法的方式之一 与继承没有任何关系 指名道姓的调用
        # super(Student, self).__init__(name,sex,age)# super表示父类的意思 python2中的写法
        super().__init__(name,sex,age)# super()会调用父类的初始化方法 最常用写法
        self.number = number # 仅初始化不同的部分

    # 覆盖父类中的say_hi方法
    def say_hi(self):
        super().say_hi()
        print(self.number)
        print(super().test) # 调用父类中的属性

stu1 = Student("牛大儿子", "man", 100,"olboy 007")
stu1.say_hi()

组合
    即把不同的对象组合到一起 也是用来减少重复代码

    武器:属性:名字 攻击力 被动
          技能:开火
组合:一个对象 可以把另一个对象作为属性来使用

 

class WQ:
    def __init__(self,name,attack,bd):
        self.name = name
        self.attack = attack
        self.bd =bd

    def fire(self):
        print(self.name,"开火。。。。")

    def show_info(self):
        print(self.name)

class Hero:
    group = "demaxiya"

    # 英雄需要有武器属性
    # wq = WQ("意大利炮","0","可以打自己人")

    def __init__(self,name,HP,MP):
        self.name = name
        self.HP = HP
        self.MP = MP

    def attack(self):
        self.wq.fire()

    def get_wq(self,name,attack,bd):
        self.wq = WQ(name,attack,bd)

h = Hero("李云龙",1000,500)
h.get_wq("圆月弯刀",500,"没有")
h.attack()

h1 = Hero("楚云飞",1000,500)
h1.get_wq("小李飞刀",600,"没有")
h1.attack()

h1.wq.fire()
h1.wq.show_info()

组合 一个对象把另一个对象作为属性
描述的时什么有什么的关系

class PC:
    def __init__(self,pc_type):
        self.pc_type = pc_type

    def working(self):
        print("%s 计算机正在计算" % self.pc_type)

class Student():
    def __init__(self,name,pc):
        self.name = name
        self.pc = pc

    def studying(self):
        self.pc.working()
        print("%s 使用%s 电脑在听课" % (self.name,self.pc.pc_type))

pc1 = PC("联想")
stu1 = Student("abc",pc1)
stu1.studying()

python支持多继承
一个类可以同时继承多个其他类
好处:可以同时拥有多个类中已存在的内容
坏处:如果父类中出现了重复的名字  执行顺序需要参考mro列表
     查看mro列表 类名.mro()

class Person:
    def study(self):
        print("人要具备学习能力")

    def sleep(self):
        print("人 躺着睡")
    pass
class Animal:
    def eat(self):
        print("动物要具备吃的能力")

    def sleep(self):
        print("站着睡")
    pass

class Student(Animal,Person):
    pass

stu1 = Student()
stu1.eat()
stu1.study()
# 默认情况下 是按照继承顺序来访问属性
stu1.sleep()

经典类和新式类 在访问顺序上有所不同
经典类 按照深度优先的顺序
新式类 也是按照深度优先 遇到公共父类则 找另一条继承关系 最后才会找公共父类

事例:

class A:
    s = 1
    pass

class B(A):
    # s = 2
    pass

class C(A):
    # s = 3
    pass

class D(A):
    # s = 4
    pass

class E(D,C,B):
    # s = 5
    pass

e = E()
print(e.s)

#
print(E.mro())