继承介绍
继承是一种新建类的方式,继承了一个类,类中的属性和方法就在子类中
类分为父类(基类)以及子类(派生类)其中子类可以继承父类
新式类
只要继承了object类,就是新式类,再Python3中默认继承object类
经典类
没有继承object的类,就是经典类
python3中因为默认继承object类,所以不存在经典类,而python2中则既有新式类又有经典类
继承方法
下面主要用代码来表示一下继承的方法
class A(object): pass class C: pass # B继承了A这个类 class B(A, C): pass # 类的其他内置属性 __名字__ # print(B.__dict__) # 类名 # print(B.__name__) # B # B的父类 print(B.__bases__) # (<class '__main__.A'>, <class '__main__.C'>)
可以看到,class 类名(类名)就是继承的格式,
利用继承减少代码冗余
当多个类中的某条属性或者方法相同时,我们可以创建一个父类,将这些方法或者属性写在父类里,这样子的话就可以减少多个子类里的相同代码了
重用父类属性
class Person: school = '哈佛大学' class Teacher(Person): def __init__(self,name,age,level): self.name=name self.age=age self.level=level class Student(Person): # school = 'xxx' def __init__(self,name,age,course): self.name=name self.age=age self.course=course
这就是一个父类Person以及俩个子类,当子类拥有共同的学校的时候,就可以写在父类中
stu1=Student('wed',19,"Python") # stu1.school='xxx' print(stu1.school)
这时同样调用Student类的对象就会有学校。同样在调用对象后也可以改变对象的属性和方法
属性的查找顺序
先找对象----》类中找-----》父类中找(多继承)-----》报错
重用父类方法
和重用父类属性类似
class Person(object): school = 'oldboy' def __init__(self, name, age): self.name = name self.age = age class Teacher(Person): pass class Student(Person): pass stu1 = Student('nick', 18) # stu1.school='xxx' print(stu1.school)
多层继承
顾名思义,就是一层一层的继承上去,直到找到想要的属性或者方法为止
class A: # a="AAAA" pass class B: # a="BBB" pass class C: a="CCC" pass class D(A,B,C): # a = "DDD" pass d=D() print(d.a)
如果D中的变量a被注释,则找C中的,C中的被注释,则找B中的。。。依次推类
多维承
class A: # a="AAAA" pass class B: # a="BBB" pass class C: a="CCC" pass class D(A,B,C): # a = "DDD" pass d=D() print(d.a)
多维承则是寻找最高的父类中的属性,如果A中没有则找B,依次推类
多维承的多层
主要是维承的菱形问题,其中新式类和经典类的查找顺序是不一样的
新式类
新式类的查找顺序:广度优先---从左侧开始,一直往上找,找到菱形的顶点结束(不包括菱形顶点),继续下一个继承的父类往上找,找到菱形的顶点结束(不包括菱形顶点),最后找到菱形顶点
经典类
深度优先---从左侧开始,一直往上找,找到菱形的顶点结束(包括菱形顶点)继续下一个继承的父类往上找,找到菱形的顶点结束(不包含菱形定点)
没有菱形问题时则正常查找
重用父类方法
继承重用父类方法方式一:指名道姓的使用
跟继承没有关系
class A: def __init__(self,name,age): self.name=name self.age=age class Person: school = '哈佛大学' def __init__(self,name,age): self.name=name self.age=age def study(self): print('study....') class Teacher(Person): def __init__(self,name,age,level): A.__init__(self,name,age) # self.name=name # self.age=age self.level=level class Student(Person): school = 'yyyy' def __init__(self,name,age,course): #如何重用父类的__init__方法 Person.__init__(self,name,age) self.course=course def study(self): Person.study(self) print("%s学生在学习"%self.name) stu1=Student('wed',19,"Python") # stu1.school='xxx' print(stu1.school) stu1.study()
指名道姓的方式在什么情况下用?
1 没有继承关系
2 如果继承了多个父类,super是按照mro列表找,现在想指名道姓的用某个父类的某个方法,就需要指名道姓的使用
重用父类方法的第二种方式
通过super关键字来执行,和继承有关系
class Person(object): school = '哈佛大学' def __init__(self,name,age): self.name=name self.age=age def study(self): print('study....') class Student(Person): school = 'yyyy' def __init__(self,name,age,course): #super() 会按照mro列表拿到父类对象 #对象来调用绑定方法,不需要传递第一个参数(self) super().__init__(name,age) #经典类和新式类 #经典类中必须这么写(py3中没有经典类),都用上面那种方式写 # super(Student,self).__init__(name,age) self.course=course def study(self): # Person.study(self) super().study() # print("%s学生在学习"%self.name) stu1=Student('wed',19,"Python") # stu1.school='xxx' # print(stu1.school) stu1.study() # study....
super()相当于得到了一个特殊对象,第一个参数不需要传,调用绑定方法,会把自己传过去
self不需要传,不需要传
来源:https://www.cnblogs.com/jie9527-/p/11448323.html