zoukankan      html  css  js  c++  java
  • day30-mixin、重载、多态、绑定与非绑定方法、内置函数

    内容回顾

    上节课复习
        1、继承
            优点:解决类与类之间代码冗余问题
            缺点:将类耦合到了一起
    
    
        2、python支持多继承
            优点:最大程度地重用父类的属性
            缺点:
                1、违背人的思维习惯:继承表达的是一种什么"是"什么的关系
                2、代码可读性会变差
                3、不建议使用多继承,有可能会引发可恶的菱形问题,扩展性变差,
                如果真的涉及到一个子类不可避免地要重用多个父类的属性,应该使用Mixins
            class A(object): # A.mro()
                pass
    
            class B(A): # B.mro()
                pass
    
            class C(B) # C.mro()
                pass
    
            obj=B()
            B.xxx
            obj.xxx
    
        2、派生:子类中衍生出的新东西
            1、子类独有,父类没有
            2、子类有,父类也有,子类是完全覆盖父类的
            3、子类有,父类也有,子类是在父类的基础上进行拓展
    
    
            ps:在子类派生的新方法中如何重用父类的功能
            class A(object):
                def f1(self):
                    pass
    
            class B(A):
                def f1(self):
                    A.f1(self)
                    拓展的代码
    
    
    今日内容:
        1、多继承的正确打开方式:mixins机制
        2、在子类派生的新方法中如何重用父类的功能
            方式一:指名道姓调用某一个类下的函数=》不依赖于继承关系
            方式二:super()调用父类提供给自己的方法=》严格依赖继承关系
        3、多态与鸭子类型
        4、绑定方法与非绑定方法
            classmethod
            staticmethod
    
        5、内置函数
    

    mixin机制

    """
    @作者: egon老湿
    @微信:18611453110
    @专栏: https://zhuanlan.zhihu.com/c_1189883314197168128
    """
    
    # 多继承的正确打开方式:mixins机制
    # mixins机制核心:就是在多继承背景下尽可能地提升多继承的可读性
    # ps:让多继承满足人的思维习惯=》什么"是"什么
    class Vehicle:
        pass
    
    class FlyableMixin:
        def fly(self):
            pass
    
    class CivilAircraft(FlyableMixin,Vehicle):  # 民航飞机
        pass
    
    class Helicopter(FlyableMixin,Vehicle):  # 直升飞机
        pass
    
    class Car(Vehicle):  # 汽车并不会飞,但按照上述继承关系,汽车也能飞了
        pass
    
    
    import socketserver
    # 补充:通常Mixin结果的类放在左边
    

    在子类派生的新方法中如何重用父类的功能

    在子类派生的新方法中如何重用父类的功能
    方式一:指名道姓调用某一个类下的函数 =》不依赖于继承关系
    
    
    class OldboyPeople:
        def __init__(self, name, age, sex):
            self.name = name
            self.age = age
            self.sex = sex
    
        def f1(self):
            print('%s say hello' % self.name)
    
    
    class Teacher(OldboyPeople):
        def __init__(self, name, age, sex, level, salary):
            OldboyPeople.__init__(self, name, age, sex)
    
            self.level = level
            self.salary = salary
    
    
    tea_obj = Teacher('egon', 18, 'male', 10, 3000)
    print(tea_obj.__dict__)
    
    方式二:super()调用父类提供给自己的方法 =》严格依赖继承关系
    调用super()会得到一个特殊的对象,该对象会参照发起属性查找的那个类的mro, 去当前类的父类中找属性
    
    
    class OldboyPeople:
        def __init__(self, name, age, sex):
            self.name = name
            self.age = age
            self.sex = sex
    
        def f1(self):
            print('%s say hello' % self.name)
    
    
    class Teacher(OldboyPeople):
        def __init__(self, name, age, sex, level, salary):
            # super(Teacher,self).__init__(name,age,sex)
            super().__init__(name, age, sex)  # 调用的是方法,自动传入对象
    
            self.level = level
            self.salary = salary
    
    
    # print(Teacher.mro())
    tea_obj = Teacher('egon', 18, 'male', 10, 3000)
    print(tea_obj.__dict__)
    
    
    super()案例
    
    
    class A:
        def test(self):
            print('from A')
            super().test()
    
    
    class B:
        def test(self):
            print('from B')
    
    
    class C(A, B):
        pass
    
    
    obj = C()
    obj.test()
    
    print(C.mro())
    
    
    class A:
        def test(self):
            print('from A')
            super().test1()
    
    
    class B:
        def test(self):
            print('from B')
    
    
    class C(A, B):
        def test1(self):
            print('from C')
    
    
    obj = C()
    obj.test()
    
    print(C.mro())
    
    

    多态

    1、什么多态:同一事物有多种形态
    
    
    class Animal:
        pass
    
    
    class People(Animal):
        pass
    
    
    class Dog(Animal):
        pass
    
    
    class Pig(Animal):
        pass
    
    
    2、为何要有多态 =》多态会带来什么样的特性,多态性
    多态性指的是可以在不考虑对象具体类型的情况下而直接使用对象
    
    
    class Animal:  # 统一所有子类的方法
        def say(self):
            print('动物基本的发声频率。。。', end=' ')
    
    
    class People(Animal):
        def say(self):
            super().say()
            print('嘤嘤嘤嘤嘤嘤嘤')
    
    
    class Dog(Animal):
        def say(self):
            super().say()
            print('汪汪汪')
    
    
    class Pig(Animal):
        def say(self):
            super().say()
            print('哼哼哼')
    
    
    obj1 = People()
    obj2 = Dog()
    obj3 = Pig()
    
    
    obj1.say()
    obj2.say()
    obj3.say()
    
    定义统一的接口,接收传入的动物对象
    
    
    def animal_say(animal):
        animal.say()
    
    
    animal_say(obj1)
    animal_say(obj2)
    animal_say(obj3)
    
    
    print('hello'.__len__())
    print([1, 2, 3].__len__())
    print({'a': 1, 'b': 2}.__len__())
    
    
    def my_len(val):
        return val.__len__()
    
    
    print(my_len('hello'))
    print(my_len([1, 2, 3]))
    print(my_len({'a': 1, 'b': 2}))
    
    len('hello')
    len([1, 2, 3])
    len({'a': 1, 'b': 2})
    
    
    python推崇的是鸭子类型
    
    
    class Cpu:
        def read(self):
            print('cpu read')
    
        def write(self):
            print('cpu write')
    
    
    class Mem:
        def read(self):
            print('mem read')
    
        def write(self):
            print('mem write')
    
    
    class Txt:
        def read(self):
            print('txt read')
    
        def write(self):
            print('txt write')
    
    
    obj1 = Cpu()
    obj2 = Mem()
    obj3 = Txt()
    
    obj1.read()
    obj1.write()
    
    obj2.read()
    obj2.write()
    
    obj3.read()
    obj3.write()
    
    
    了解:
    
    
    class Animal(metaclass=abc.ABCMeta):  # 统一所有子类的标准
        @abc.abstractmethod
        def say(self):
            pass
    
    # obj=Animal() # 不能实例化抽象类自己
    
    
    class People(Animal):
        def say(self):
            pass
    
    
    class Dog(Animal):
        def say(self):
            pass
    
    
    class Pig(Animal):
        def say(self):
            pass
    
    
    obj1 = People()
    obj2 = Dog()
    obj3 = Pig()
    
    

    绑定方法和非绑定方法

    一:绑定方法:特殊之处在于将调用者本身当做第一个参数自动传入
    1、绑定给对象的方法:调用者是对象,自动传入的是对象
    2、绑定给类的方法:调用者类,自动传入的是类
    
    
    class Mysql:
        def __init__(self, ip, port):
            self.ip = ip
            self.port = port
    
        def func(self):
            print('%s:%s' % (self.ip, self.port))
    
        @classmethod  # 将下面的函数装饰成绑定给类的方法
        def from_conf(cls):
            print(cls)
            return cls(settings.IP, settings.PORT)
    
    # obj1=Mysql('1.1.1.1',3306)
    
    
    obj2 = Mysql.from_conf()
    print(obj2.__dict__)
    
    二:非绑定方法 -》静态方法:
    没有绑定给任何人:调用者可以是类、对象,没有自动传参的效果
    
    
    class Mysql:
        def __init__(self, ip, port):
            self.nid = self.create_id()
            self.ip = ip
            self.port = port
    
        @staticmethod  # 将下述函数装饰成一个静态方法
        def create_id():
            import uuid
            return uuid.uuid4()
    
        @classmethod
        def f1(cls):
            pass
    
        def f2(self):
            pass
    
    
    obj1 = Mysql('1.1.1.1', 3306)
    
    print(Mysql.create_id)
    print(obj1.create_id)
    
    Mysql.create_id(1, 2, 3)
    obj1.create_id(4, 5, 6)
    
    print(Mysql.create_id)
    print(Mysql.f1)
    print(obj1.f2)
    
    

    内置函数

    print(abs(-1))
    print(all([1, 'aaa', '1']))
    print(all([]))
    
    print(any([0, None, 1]))
    print(any([]))
    
    print(bin(11))
    print(oct(11))
    print(hex(11))
    
    print(bool(''))
    
    
    def func():
        pass
    
    
    class Foo:
        pass
    
    
    print(callable(Foo))  # 方
    
    print(chr(65))
    print(ord('A'))
    
    不可变集合
    s = frozenset({1, 2, 3})
    
    hash(不可变类型)
    
    print(round(1.5))
    print(round(1.4))
    
    
    10 ** 2 % 3
    print(pow(10, 2, 3))
    s = slice(1, 4, 2)
    l1 = ['a', 'b', 'c', 'd', 'e']
    l2 = ['aaa', 'bbb', 'ccc', 'ddd', 444]
    
    print(l1[1:4:2])  # l1[s]
    print(l2[1:4:2])  # l2[s]
    
    
    == == == == == == == == =》掌握
    v1 = 'hello'
    v2 = [111, 222, 333, 444, 5555, 6666]
    res = zip(v1, v2)
    print(list(res))
    
    == == == == == == == == =》掌握
    print(divmod(10000, 33))
    
    == == == == == == == == =》掌握
    
    
    class Foo:
        pass
    
    
    obj = Foo()
    obj.xxx = 1111
    print(dir(obj))  # obj.哪些属性
    
    == == == == == == == == =》掌握
    for i, v in enumerate(['a', 'b', 'c']):
        print(i, v)
    
    == == == == == == == == =》掌握
    res = eval('{"a":1}')  # 执行字符串中的表达式
    print(res, type(res))
    
    
    == == == == == == == == =》掌握
    
    
    class Foo:
        pass
    
    
    obj = Foo()
    print(isinstance(obj, Foo))
    print(isinstance([], list))  # 类型判断推荐使用isinstance
    print(type([]) is list)  # 不推荐使用
    
    == == == == == == == == =》掌握
    time = __import__('time')
    time.sleep(3)
    
    下个周:反射
    setattr
    getattr
    delattr
    hasattr
    
    

    作业

    本周作业:综合应用面向对象
    
    角色:学校、学员、课程、讲师
    要求:
    1. 创建北京、上海 2 所学校
    2. 创建linux , python , go 3个课程 , linuxpy 在北京开, go 在上海开
    3. 课程包含,周期,价格,通过学校创建课程
    4. 通过学校创建班级, 班级关联课程、讲师
    5. 创建学员时,选择学校,关联班级
    5. 创建讲师角色时要关联学校,
    6. 提供两个角色接口
    6.1 学员视图, 可以注册, 交学费, 选择班级,
    6.2 讲师视图, 讲师可管理自己的班级, 上课时选择班级, 查看班级学员列表 , 修改所管理的学员的成绩
    6.3 管理视图,创建讲师, 创建班级,创建课程
    
    7. 上面的操作产生的数据都通过pickle序列化保存到文件里
    
  • 相关阅读:
    WCF系列教程之WCF服务配置工具
    WCF系列教程之WCF服务配置
    C# 多线程系列之异步回调(委托)
    WCF系列教程之消息交换模式之请求与答复模式(Request/Reply)
    C# ref与out关键字解析
    WCF系列教程之WCF消息交换模式之单项模式
    WCF系列教程之初识WCF
    C# 装箱和拆箱
    C# checked和unchecked运算符
    Specified key was too long; max key length is 1000 bytes问题解决
  • 原文地址:https://www.cnblogs.com/zdw20191029/p/14553340.html
Copyright © 2011-2022 走看看