目录
继承
1.什么是继承
继承指的是新建类的方法,新建的类称之为字类或派生类
字类继承的类叫做父类,也称之为基类或超类
继承的特征:
子类可以继承父类的属性(特征与技能),并且可以派生出自己的属性(特征与技能)
注意: 在python中,一个子类可以继承多个父类
2.为什么要继承
继承的目的是为了减少代码的冗余(减少重复代码)
3.如何实现继承
1.首先要确定谁是子类,谁是父类.
2.在定义类时,子类 + (), ()内写父类,实现继承
# 父类
class ParentClass1:
pass
class ParentClass2:
pass
# 子类
class SubClass1(ParentClass1)
pass
#查看继承的父类:__bases__, 时类的属性,用来查找当前父类
print(SubClass1.__bases__)
寻找继承关系
如何寻找继承关系:
要想寻找继承关系,首先要"先抽象,再继承"
什么是抽象?
抽象指的是抽取相似的部分,称之为抽象
继承的关系:
对象是特征与技能的结合体
类是一系列对象相同的特征与技能的结合体
继承是一系列类相同的特征与技能的结合体
继承背景下对象属性查找顺序
1.对象查找属性会从对象的名称空间中查找
2.若对象没有,则回去类里面找
3.若当前类是子类,并且没有对象找的属性,回去父类中查找
注意: 对象查找属性,若子类有,不管父类有没有,以子类为准.
# 父类
class OldboyPeople:
school = 'oldboy'
def __init__(self, name, age, sex):
self.name = name
self.age = age
self.sex = sex
# 子类
class OldboyTeacher(OldboyPeople):
# 老师修改分数技能
def change_score(self):
print(f'老师[{self.name} 修改分数...]')
tea1 = OldboyTeacher('tank', 17, 'male')
print(tea1.school)
# 查看对象名称空间
print(tea1.__dict__)
# __class__: 对象的属性,查看当前对象的类.
# 查看子类名称空间
print(tea1.__class__.__dict__)
# 查看父类名称空间
print(tea1.__class__.__bases__[0].__dict__)
# 验证对象属性的查找顺序
class Foo:
def f1(self):
print('Foo.f1')
def f2(self):
print('Foo.f2')
self.f1()
class Soo(Foo):
def f1(self):
print('Soo.f1')
soo_obj = Soo()
soo_obj.f2()
'''
Foo.f2
Soo.f1
'''
派生
什么是派生
派生指的是子类继承父类的属性,并且派生出新的属性
子类派生出新的属性,若与父类的属性相同,则以子类为准
继承是谁与谁的关系,指的是类鱼类的关系,子类与父类是从属关系
# 验证对象属性的查找顺序
class Foo:
def f1(self):
print('Foo.f1')
def f2(self):
print('Foo.f2')
self.f1()
class Soo(Foo):
def f1(self):
print('Soo.f1')
soo_obj = Soo()
soo_obj.f1() # Soo.f1
子类派生出新的属性,并重用父
方式一:
直接通过 父类.(调用)_init_,把__init__当作普通函数使用,传入对象与继承的属性
方式一:
class OldboyTeacher(OldboyPeople):
# 等级, 薪资
def __init__(self, name, age, sex, level, sal):
OldboyPeople.__init__(self, name, age, sex)
self.level = level
self.sal = sal
class OldboyStudent(OldboyPeople):
# 课程
def __init__(self, name, age, sex, course):
OldboyPeople.__init__(self, name, age, sex)
self.course = course
def choose_course(self):
print(f'学生{self.name}选择课程{self.course}')
方式二:
super是一个特殊的类,在子类中调用super()
class OldboyTeacher(OldboyPeople):
# 等级, 薪资
def __init__(self, name, age, sex, level, sal):
super().__init__(name, age, sex)
self.level = level
self.sal = sal
class OldboyStudent(OldboyPeople):
# 课程
def __init__(self, name, age, sex, course):
super().__init__(name, age, sex)
self.course = course
def choose_course(self):
print(f'学生{self.name}选择课程{self.course}')
新式类和经典类
了解:
在python2中,才会有新式类和经典类之分.
在python3中,所有的类都是新式类
新式类:
继承object的类都称之为新式类.
python3中,子类不继承自定义的类时,默认继承object.
经典类
在python2 中,凡是没有继承object的类都是经典类.
菱形继承
在多继承的情况下形成了菱形继承
经典类
深度优先
新式类
广度优先
通过继承实现修改json模块数据类型
import json
from datetime import date,datetime
print(json.JSONEncoder)
print(datetime.today()) # 当前时间
print(date.today()) # 当前时间
# isinstance:
# python内置的函数,可以传两个参数,判断参数一是否是参数二的一个实例
# 开源者的角度: 修改json源码
class MyJson(json.JSONEnocoder):
def default(self,o):
# 子类派生的功能
# 判断o是否是datetime的一个实例
if isinstance(o,datetime):
return o.strtime('%Y-%m-%d %X')
elif isinstance(o,date):
return o.strtime('%Y-%m-%d')
else:
# 继承父类的default方法的功能
return super().default(self,o)
dict1 = {
'name': 'tank',
'today': datetime.today(),
'today2': date.today(),
}
res = json.dumps(dict1,cls=MyJson) # cls=None,默认指向的是原json的JSONEncoder
print(res)