单继承下的属性查找
# 单继承的意思是一个类只继承一个类
class D():
pass
class C(D):
pass
class B(C):
pass
class A(B):
pass
"""python支持多继承"""
class D():
pass
class C(D):
pass
class B(C):
pass
class A(B,C,D):
pass
如何查找继承下的属性和方法呢
# class Foo():
# def f1(self):
# print("Foo.f1")
#
# def f2(self):
# # obj:
# print("Foo.f2")
# self.f1()
#
#
# class Bar(Foo):
# def f1(self):
# print("Bar.f1")
#
#
# """单继承下的属性查找顺序:先从对象自己的名称空间中查找,然后去产生这个对象的类中查找,最后在去继承的父类中查找"""
# obj = Bar()
# obj.f2() # obj.f2(obj)
class Foo():
def __f1(self): # _Foo__f1()
print("Foo.f1")
def f2(self):
# obj:
print("Foo.f2")
self.__f1() # self._Foo__f1()
class Bar(Foo):
def __f1(self): # _Bar__f1()
print("Bar.f1")
"""单继承下的属性查找顺序:先从对象自己的名称空间中查找,然后去产生这个对象的类中查找,最后在去继承的父类中查找"""
obj = Bar()
obj.f2() # obj.f2(obj)
多继承下的属性查找
# 一个类可以继承多个类
"""python支持多继承"""
class D():
pass
class C(D):
pass
class B(C, D):
pass
class A(B,C,D):
pass
"""多继承下的属性查找分为:菱形查找和非菱形查找"""
# 菱形查找分:经典类和新式类
经典类:按照深度优先查询
新式类:按照的广度优先查询
"""在python3中都是新式类,所以,多继承下的属性查找,如果属性找不到,就按照广度优先查询"""
# 一般情况下,最好不使用多继承
# drf中的多继承很好明白
super关键字的使用
class A:
def test(self):
super().test()
class B:
def test(self):
print('from B')
class C(A, B):
pass
# c = C()
# c.test() # from B
a = A()
a.test()
"""mro列表"""
# mro列表就是C类的属性查找顺序
"""
如果你继承的类中出现了super()关键字的用法,就要使用mro列表来查找属性
"""
# print(C.mro()) # [<class '__main__.C'>, <class '__main__.A'>, <class '__main__.B'>, <class 'object'>]
# print(A.mro()) # [<class '__main__.A'>, <class 'object'>]
# print(A.__mro__)
多态与多态性(理论)
多态:一种事物的多种形态
eg:
水:液态水、气态水、固态水
动物:人、狗、猫、猪...
"""如何在父类里面强制限制子类中必须有speak功能"""
class Animal():
def speak():
pass
class People(Animal):
def speak():
pass
class Dog(Animal):
def speak():
pass
class Pig(Animal):
def speak():
pass
obj = People()
obj.speak()
"""如何在父类里面强制限制子类中必须有speak功能"""
import abc # abstract 抽象的
# 这个类就变成了:抽象类
# 抽象类的特点:只能被继承,不能被实例化!
# 抽象类中的方法都是抽象方法,而抽象方法不再实现具体的功能,而是用来限制子类的行为
"""强制限制,这种方式是python不推荐的,python推荐的是鸭子类型"""
# class Animal(metaclass=abc.ABCMeta):
# @abc.abstractmethod # 抽象方法
# def speak(self):
# pass
#
# @abc.abstractmethod
# def jiao(self):
# pass
#
# class People(Animal):
# def speak(self):
# pass
# ...
#
# class Dog(Animal):
# def speak(self):
# pass
#
# class Pig(Animal):
# def speak(self):
# pass
#
# obj = People()
# obj1 = Dog()
# obj.speak()
# obj1.speak()
组合
# 组合它不是一个新技术,就是之前我们学习的知识点
组合:就是一个对象拥有一个属性,该属性的值是另外一个对象
# class Foo():
# def __init__(self, m):
# self.m = m
#
#
#
# class Bar():
# def __init__(self, n):
# self.n = n
#
#
# obj = Foo(10)
# obj1 = Bar(20)
#
# """obj对象就是一个超级对象,通过一个对象可以得到另外一个对象的值"""
# obj.x = obj1
# # obj.x ---------> obj1
# print(obj1.n)
# # print(obj.x.n)
# print(obj.x.n) # print(obj1.n)
class People():
def __init__(self, name, age, gender):
"""这个是指名道姓的调用方法,不依赖于继承"""
self.name = name
self.age = age
self.gender = gender
"""
继承一般用在什么是什么的时候
组合一般用在什么有什么的时候
"""
class Course():
def __init__(self, course_name, course_price, course_period):
"""这个是指名道姓的调用方法,不依赖于继承"""
self.course_name = course_name
self.course_price = course_price
self.course_period = course_period
python=Course("python", 10000, '6mon')
linux = Course("linux", 20000, '5mon')
class Student(People):
def __init__(self, name, age, gender, course=None):
if course is None:
course = []
"""这个是指名道姓的调用方法,不依赖于继承"""
super(Student, self).__init__( name, age, gender)
self.courses = course
def choose_course(self):
pass
stu = Student('kevin', '19', 'male')
# print(stu.course_name)
# print(stu.course_price)
stu.courses.append(python) # stu.courses ====> [python对象]
stu.courses.append(linux) # stu.courses ====> [python对象, linux对象]
print(stu.courses)