zoukankan      html  css  js  c++  java
  • 继承和接口与归一化设计

    继承和接口与归一化设计

    返回首页

    继承

    继承是一种创建新的类的方式,在python中,新建的类可以继承自一个或多个父类,原始类被称为基类或超类,新建的类被称为派生类或子类。

    class ParentClass1: #定义父类
        pass
    
    class ParentClass2: #定义父类
        pass
    
    class SubClass1(ParentClass1): #单继承,基类是ParentClass1,派生类是SubClass
        pass
    
    class SubClass2(ParentClass1,ParentClass2): #python支持多继承,用逗号分隔开多个继承的类
        pass
    
    print(ParentClass1.__bases__)
    print(SubClass1.__bases__)
    print(SubClass2.__bases__)

    继承与抽象

    抽象即是抽取类似或者比较像的部分,抽象分为两个层次。

    1、将奥巴马和梅西这俩对象比较像的部分抽取成类。

    2、将人、猪、狗这三个类比较像的部分抽取成父类

    抽象最主要的作用是划分类别(可以隔离关注点,降低复杂度)

    继承是基于抽象的结果,通过编程语言去实现它,肯定是先经历抽象这个过程,才能通过继承的方式去表达出抽象的结构。

    class Aniaml:
        def __init__(self,name,age):
            self.name = name
            self.age = age
    
        def walk(self):
            print('%s is walking' %self.name)
    
        def say(self):
            print('%s is saying' %self.name)
    
    class People(Aniaml):
        pass
    
    class Pig(Aniaml):
        pass
    
    class Dog(Aniaml):
        pass
    
    p1 = People('obama',50) #people没有name和age,但是people继承了animal,所以可以使用animal的name和age
    print(p1.name)
    print(p1.age)
    p1.walk()

    继承可以解决重用性。

    上面的例子就说明了重用性,在people类中,不用再写walk和say,在继承的父类animal中调用即可。

    派生

    派生就是将类共有的属性(特征)和函数(技能)单独取出,作为一个父类后,子类里在添加的属性和函数,就是派生。派生出类自己的东西。 

    class Hero:
        def __init__(self, nickname,aggressivity,life_value):
            self.nickname = nickname
            self.aggressivity = aggressivity
            self.life_value = life_value
        def attack(self, enemy):
            print('Hero attack')
    
    class Garen(Hero):
        camp = 'Demacia'
        def attack(self, enemy): #self=g1,enemy=r1
            # self.attack(enemy) #g1.attack()
            Hero.attack(self,enemy)    #用父类里的attack,参数是Hero里的attack的参数。这里的self是g1,enemy是r1
            print('from garen attack')
    
        def fire(self):
            print('%s is firing' % self.nickname)
    
    class Riven(Hero):
        camp = 'Noxus'
    
    g1 = Garen('garen', 18, 200)
    r1 = Riven('rivren', 18, 200)
    g1.attack(r1)
    print(g1.camp)
    print(r1.camp)
    g1.fire()

    组合

    组合是类与类之间有的关系, 当类之间有着明显不同,并且较小的类是较大的类所需要的组件时,用组合比较好。

    接口与归一化设计

    在python中,没有接口的概念。而接口的概念,简单的说就是对外的入口。所以在python中,要实现接口的效果,只能用继承去模拟。

    在继承中,父类不用去实现具体的功能,而是在子类中,具体的去实现。

    class Interface:#定义接口Interface类来模仿接口的概念,python中压根就没有interface关键字来定义一个接口。
        def read(self): #定接口函数read
            pass
    
        def write(self): #定义接口函数write
            pass
    
    class Txt(Interface): #文本,具体实现read和write
        def read(self):
            print('文本数据的读取方法')
    
        def write(self):
            print('文本数据的写入方法')
    
    class Sata(Interface): #磁盘,具体实现read和write
        def read(self):
            print('硬盘数据的读取方法')
    
        def write(self):
            print('硬盘数据的写入方法')
    
    class Process(Interface):
        def read(self):
            print('进程数据的读取方法')
    
        def write(self):
            print('进程数据的写入方法')
    
    t1=Txt()
    s1=Sata()
    p1=Process()
    t1.read()
    t1.write()
    s1.read()
    s1.write()
    p1.read()
    p1.write()

    抽象

    import abc
    #抽象类:本质还是类,与普通类额外的特点的是:加了装饰器的函数,子类必须实现他们
    class Animal(metaclass=abc.ABCMeta):
        tag='123123123123123'
        @abc.abstractmethod
        def run(self):
            pass
        @abc.abstractmethod
        def speak(self):
            pass
    
    class People(Animal):
        def run(self):
            pass
    
        def speak(self):
            pass
    
    peo1=People()
    print(peo1.tag)

    继承的顺序

    继承的顺序分为python2和python3。

    在python2中,经典类和新式类的继承方式是不同的。

    py2中,经典类的多继承顺序是:优先深度查找。新式类的多继承顺序是:优先广度查找。

    在py3中,只有新式类,所以py3只有广度优先查找。

    新式类:

     #新式类的继承,在查找属性时遵循:广度优先
    class A(object):
        def test(self):
            print('from A')
    class B(A):
        def test(self):
            print('from B')
    class C(A):
        def test(self):
            print('from C')
    class D(B):
        def test(self):
            print('from D')
    class E(C):
        def test(self):
            print('from E')
    class F(D,E):
        def test(self):
            print('from F')
    f1=F()
    f1.test()
    
    print(F.__mro__)
    print(F.mro())
    
    #广度优先:F->D->B->E->C->A->object

    经典类:

    #python2中经典类的继承,在查找属性时遵循:深度优先
    class A:
        number = 10
        def test(self):
            print('from A')
    
    class B(A):
        def test(self):
            print('from B')
    
    class C(A):
        def test(self):
            print('from C')
    
    class D(B):
        def test(self):
            print('from D')
    
    class E(C):
        def test(self):
            print('from E')
    
    class F(D,E):
        def test(self):
            print('from F')
    
    f1=F()
    f1.test()
    print(f1.number)
    
    ###F->D->B->A->E->C

    super函数

    子类调用父类的方法,用super方法。

    除了在子类中,用类名.的方法调用父类方法外,还可以用super方法。

    #在python3中
    class People:
        def __init__(self,name,sex,age):
            self.name=name
            self.age=age
            self.sex=sex
    
        def walk(self):
            print('%s is walking' %self.name)
    
    class Chinese(People):
        country='China'
        def __init__(self,name,sex,age,language='Chinese'):
            # self.name=name
            # self.sex=sex
            # self.age=age
            # People.__init__(self,name,sex,age)
            super(Chinese,self).__init__(name,sex,age) #super()相当于一个对象,super().__init__相当于是调用对象的绑定方法。也就是调用父类的绑定方法。
            self.language=language
    
        def walk(self,x):
            super().walk()
            print('子类的x',x)
    
    c=Chinese('egon','male',18)
    print(c.name,c.age,c.sex,c.language)
    c.walk(123)

    ---------- END ---------

  • 相关阅读:
    Software_Kingjdk配置java
    SSH中的分页错误:java.lang.Integer cannot be cast to java.lang.Long
    struts2中文件上传出错!
    Navicat Premium(导航猫数据库管理)navicat091_premium_cs + instantclientbasic
    org.springframework.dao.InvalidDataAccessApiUsageException: Write operations are not allowed in readonly mode (FlushMode.NEVER/MANUAL): Turn your Ses
    OAS2Sh项目中:java.lang.IllegalArgumentException: id to load is required for loading
    python之封装
    python函数中的装饰器
    OSI七层模型
    函数
  • 原文地址:https://www.cnblogs.com/george92/p/14573909.html
Copyright © 2011-2022 走看看