• python mro 、 super()获得父类定义


    MRO(method resolution order)

    Python 支持多继承,如果父类中有相同名字的方法,在子类中没有指定父类名字的时候,解释器将根据 从左到右 按顺序搜索。 我们可以通过 类.mro() 来获得类的层次结构图 ,方法 的解析顺序也是按照这个来的。

    class A:
        def aa(self):
            print("aa")
    
        def say(self):
            print("aa")
    
    class B:
        def bb(self):
            print("bb")
        def say(self):
            print("bb")
    
    class C(B,A):
        def cc(self):
            print("cc")
    
    c = C()
    print(C.mro())
    c.say()
    

    [<class ‘main.C’>, <class ‘main.B’>, <class ‘main.A’>, <class ‘object’>]
    bb

    super()

    class A:
        def aa(self):
            print("aa")
    
        def say(self):
            print("aa")
    
    class B(A):
        def bb(self):
            print("bb")
    
        def say(self):
            super().say()
            print("bb")
    
    
    
    b = B()
    b.say()
    

    aa
    bb

    多态

    class Animal:
        def shout(self):
            print("动物叫了")
    
    class Cat(Animal):
        def shout(self):
            print("小猫叫了")
    
    class Dog(Animal):
        def shout(self):
            print("小狗叫了")
    
    
    def animalShout(a):
        if isinstance(a,Animal):
            a.shout()
    
    animalShout(Dog())
    animalShout(Cat())
    

    小狗叫了
    小猫叫了

    特殊方法跟运算符重载

    Python中的符号运算都是通过调用特殊方法来实现的比如

    a = 20
    b = 30
    c = a + b
    d = a.__add__(b)
    
    print("c=",c)
    print("d=",d)
    

    50
    50
    在这里插入图片描述
    在这里插入图片描述
    在这里插入图片描述

    重写若干方法 实现运算符的重载

    class Person:
        def __init__(self,name):
            self.name = name
    
        def __add__(self, other):
            if isinstance(other,Person):
                return "{0}--{1}".format(self.name,other.name)
            else:
                return "不是同类对象 不可以相加"
    
        def __mul__(self, other):
            if isinstance(other,int):
                return self.name*other
            else:
                return "不是同类对象 不可以相加"
    
    p1 = Person("sowhat")
    p2 = Person("student")
    
    x = p1 + p2
    print(x)
    
    print(p1*3)
    

    sowhat–student
    sowhatsowhatsowhat

    特殊属性

    Python对象中 还包含很多双下划线开始跟结束的属性,如下:
    在这里插入图片描述

    class A:
        pass
    
    class B:
        pass
    
    class C(B,A):
        def __init__(self,n):
            self.n = n
    
        def cc(self):
            print("cc")
    
    c = C(3)
    print(dir(c))
    print(c.__dict__)
    print(c.__class__)
    print(C.__bases__)
    print(C.mro())
    print(A.__subclasses__())
    

    [‘class’, ‘delattr’, ‘dict’, ‘dir’, ‘doc’, ‘eq’, ‘format’, ‘ge’, ‘getattribute’, ‘gt’, ‘hash’, ‘init’, ‘init_subclass’, ‘le’, ‘lt’, ‘module’, ‘ne’, ‘new’, ‘reduce’, ‘reduce_ex’, ‘repr’, ‘setattr’, ‘sizeof’, ‘str’, ‘subclasshook’, ‘weakref’, ‘cc’, ‘n’]
    {‘n’: 3}
    <class ‘main.C’>
    (<class ‘main.B’>, <class ‘main.A’>)
    [<class ‘main.C’>, <class ‘main.B’>, <class ‘main.A’>, <class ‘object’>]
    [<class ‘main.C’>]

    对象的浅拷贝跟深拷贝

    1. 变量的赋值操作:只是形成了两个变量,实际上还是指向同一个对象。
    2. 浅拷贝:Python的拷贝一般都是浅拷贝,拷贝的时候 只将原对象复制一份,原对象里的子对象内容不拷贝,因此原对象跟拷贝对象会引用同一个子对象 copy.copy()
    3. 使用copy模块的deepcopy函数,递归拷贝对象中包含的子对象,源对象跟拷贝对象中的所有子对象也是不同的。
    #coding=utf-8
    import time
    import math
    import copy
    
    class MobilePhone:
        def __init__(self,cpu,screen):
            self.cpu = cpu
            self.screen = screen
    
    class CPU:
        def calculate(self):
            print("计算,算个123")
            print("CPU对象",self)
    
    class Screen:
        def show(self):
            print("显示一个好看的画面")
            print("屏幕对象:",self)
    
    
    
    c = CPU()
    s = Screen()
    m = MobilePhone(c,s)
    m.cpu.calculate()
    
    n = m
    print(m,n) # m 跟 n 只是引用 他们指向同一个对象的
    
    
    print('='*20)
    m2 = copy.copy(m)
    
    print(m,m2) #  浅拷贝 地址不同了
    m.cpu.calculate() #  浅拷贝 子对象地址还是一样
    m2.cpu.calculate() #  浅拷贝 子对象地址还是一样
    
    print('='*20)
    m3 = copy.deepcopy(m)
    m3.cpu.calculate()
    m.cpu.calculate()
    

    将若干不同的类组合到一起就可以实现复杂功能了。

    工厂模式

    class Benz:
        pass
    class BMW:
        pass
    class BYD:
        pass
    
    class CarFactory:
        @staticmethod
        def createCar(name):
            if name == "奔驰":
                return Benz()
            elif name == "宝马":
                return BMW()
            elif name == "比亚迪":
                return BYD()
            else:
                return "未知品牌"
    
    
    c1 = CarFactory.createCar("宝马")
    c2 = CarFactory.createCar("奔驰")
    

    单例模式

    单例模式只生成一个实例对象,减少了对系统资源的开销,当一个对象的产生需要较多资源,如读取配置文件,产生其他依赖对象时,可以产生一个单例对象,永久驻留内存。降低开销。

    #coding=utf-8
    import time
    import math
    import copy
    import threading
    
    
    class MySingleton:
       __instance_lock = threading.Lock()
       
       def __init__(self,name):
           if MySingleton.__init_flag:
               print("init")
               self.name = name
               MySingleton.__init_flag = False
    
       def __new__(cls, *args, **kwargs):
           '''
    
           :param args:
           :param kwargs:
           :return: 对象创新的时候先调用new 方法 如果类没有写 会调用 object 中的new 方法,然后 再调用 init 方法进行初始化
           因此 如果单例模式的话一般也是在此进行设置
           '''
           print(123)
           with MySingleton.__instance_lock:
               if cls.__obj == None:
                   cls.__obj = object.__new__(cls)
                   print(id(cls.__obj))
               return cls.__obj
      
    
       __obj = None
       __init_flag = True
    
    
    a = MySingleton("aa")
    print(id(a))
    
    
    
  • 相关阅读:
    java中的静态变量与实例变量
    Java中的关键字this
    继承和多类的基础(C++)
    11-1:(42)接雨水
    10-2
    10-1
    9-2
    9-1
    8-2
    8-1
  • 原文地址:https://www.cnblogs.com/sowhat1412/p/12734113.html
Copyright © 2020-2023  润新知