Python—面向对象02

1.抽象类与归一化

接口,即提供给使用者来调用自己功能的方式、方法、入口

为什么要使用接口?

接口提取了一类共同的函数,可以把接口看做一个函数的集合

然后让子类去实现接口中的函数

这么做的意义在于归一化,什么叫归一化,就是只要是基于同一个接口实现的类,那么所有的这些类产生的对象在使用时,从用法上来说都一样。

归一化的好处在于:

  1. 归一化让使用者无需关心对象的类是什么,只需要的知道这些对象都具备某些功能就可以了,这极大地降低了使用者的使用难度。
  2. 归一化使得高层的外部使用者可以不加区分的处理所有接口兼容的对象集合
    1. 就好象linux的泛文件概念一样,所有东西都可以当文件处理,不必关心它是内存、磁盘、网络还是屏幕(当然,对底层设计者,当然也可以区分出“字符设备”和“块设备”,然后做出针对性的设计:细致到什么程度,视需求而定)。
    2. 再比如:我们有一个汽车接口,里面定义了汽车所有的功能,然后由本田汽车的类,奥迪汽车的类,大众汽车的类,他们都实现了汽车接口,这样就好办了,大家只需要学会了怎么开汽车,那么无论是本田,还是奥迪,还是大众我们都会开了,开的时候根本无需关心我开的是哪一类车,操作手法(函数调用)都一样

模仿interface

在python中根本就没有一个叫做interface的关键字,如果非要去模仿接口的概念

可以借助第三方模块:http://pypi.python.org/pypi/zope.interface

也可以使用继承,其实继承有两种用途

一:继承基类的方法,并且做出自己的改变或者扩展(代码重用):实践中,继承的这种用途意义并不很大,甚至常常是有害的。因为它使得子类与基类出现强耦合。

二:声明某个子类兼容于某基类,定义一个接口类(模仿java的Interface),接口类中定义了一些接口名(就是函数名)且并未实现接口的功能,子类继承接口类,并且实现接口中的功能

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('硬盘数据的读取方法')

上面的代码只是看起来像接口,其实并没有起到接口的作用,子类完全可以不用去实现接口 ,由此引出抽象类

接下来说 抽象类 >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>

抽象类

1 什么是抽象类

与java一样,python也有抽象类的概念但是同样需要借助模块实现,抽象类是一个特殊的类,它的特殊之处在于只能被继承,不能被实例化

2 为什么要有抽象类

如果说类是从一堆对象中抽取相同的内容而来的,那么抽象类就是从一堆类中抽取相同的内容而来的,内容包括数据属性和函数属性。

  比如我们有香蕉的类,有苹果的类,有桃子的类,从这些类抽取相同的内容就是水果这个抽象的类,你吃水果时,要么是吃一个具体的香蕉,要么是吃一个具体的桃子。。。。。。你永远无法吃到一个叫做水果的东西。

3 在python中实现抽象类

import abc

class Animal(metaclass=abc.ABCMeta): #只能被继承,不能被实例化
    all_type='animal'

    @abc.abstractmethod
    def run(self):  #定义抽象方法,无需实现功能,且子类必须定义 run 方法
        pass

    @abc.abstractmethod
    def eat(self):
        pass

# animal=Animal()  # TypeError: Can't instantiate abstract class Animal with abstract methods eat, run


class People(Animal):
    def run(self):
        print('people is running')

    def eat(self):
        print('people is eating')

class Pig(Animal):
    def run(self):
        print('pig is walking')

    def eat(self):
        print('pig is eating')

class Dog(Animal):
    pass

# dog1 = Dog()  # 报错 ,TypeError: Can't instantiate abstract class Dog with abstract methods eat, run 
# 没有实现抽象类里面的方法

peo1=People()
pig1=Pig()

peo1.run()  # people is running
pig1.run()  # pig is walking

print(peo1.all_type)  # animal
print(pig1.all_type)  # animal

关于接口与抽象类:

抽象类的本质,还是类。指的是一组类的相似性,包括数据属性和函数属性。

而接口只强调函数属性的相似性。

抽象类是一个介于 接口 和 抽象类 之间的概念,同时具备类和接口的部分特性,可以用来实现归一化设计。

2. 多态与多态性

多态

多态指的是一类事物有多种形态,比如,动物有多种形态:人,狗,猪

水有多种形态:气、液、固

多态性是指在不考虑实例类型的情况下使用实例,多态性分为静态多态性和动态多态性

静态多态性:如任何类型都可以用运算符+进行运算。。。。。如,str + str ,list + list, num + num

动态多态性:看如下代码

#多态:同一类事物的多种形态
import abc
class Animal(metaclass=abc.ABCMeta): #同一类事物:动物
    @abc.abstractmethod
    def talk(self):
        pass

class People(Animal): #动物的形态之一:人
    def talk(self):
        print('say hello')

class Dog(Animal): #动物的形态之二:狗
    def talk(self):
        print('say wangwang')

class Pig(Animal): #动物的形态之三:猪
    def talk(self):
        print('say aoao')

class Cat(Animal):
    def talk(self):
        print('say miamiao')

#多态性:指的是可以在不考虑对象的类型的情况下而直接使用对象
peo1=People()
dog1=Dog()
pig1=Pig()
cat1=Cat()

# peo、dog、pig都是动物,只要是动物肯定有talk方法
# 于是我们可以不用考虑它们三者的具体是什么类型,而直接使用

peo1.talk()  # say hello
dog1.talk()  # say wangwang
pig1.talk()  # say aoao

#更进一步,我们可以定义一个统一的接口来使用
def func(obj):   # 对于使用者来说,自己的代码根本无需改动
    obj.talk()

cat1 = Cat()
func(cat1)  # say miamiao
# 甚至连调用方式也无需改变,就能调用猫的talk功能
# 这样我们新增了一个形态Cat,由Cat类产生的实例cat1,使用者可以在完全不需要修改自己代码的情况下。使用和人、狗、猪一样的方式调用cat1的talk方法,即func(cat1)

多态性的好处:

灵活性:以不变应万变,不论对象千变万化,使用者都是同一种形式去调用,如func(animal)

可扩展性:通过继承animal类创建了一个新的类,使用者无需更改自己的代码,还是用func(animal)去调用

猜你喜欢

转载自www.cnblogs.com/friday69/p/9359465.html