面向对象:抽象类和接口类

Python角度:只有抽象类,没有接口类,实现接口类需要借助模块使用:abc模块中的abstractmethod和ABCMeta,声明元类metaclass = ABCMeta,且加上装饰器@abstructmethod

本质作用:代码规范,希望在子类中实现和父类方法名字完全一样的方法

Java角度:本来就支持单继承,所以就有了抽象类;没有多继承,所以为了接口隔离原则,所以创建了接口Interface,支持多继承

而Python既支持单继承也支持多继承,所以对于接口类和抽象类的区别就不那么明显,甚至在Python中没有内置接口类

接口隔离原则:使用多个专门的接口,而不使用单一的总接口。即客户端不应该依赖那些不需要的接口,比如接口类多继承的时候

接口类:python原生不支持,支持多继承,接口类中不能实现方法

例子:这是几个普通的支付类,但是没有规范,所以Applepay类的方法名不一致,所以报错,并且只在实例化后调用才报错
class Wechat:
    def pay(self,money):
        print('支付%s成功'%money)

class Alipay:
    def pay(self,money):
        print('支付%s成功'%money)

class Applepay:
    def zhifu(self,money):
        print('支付%s成功'%money)

def pay(payment,money):
    payment.pay(money)

wechat = Wechat()
ali = Alipay()
app = Applepay()
pay(wechat,100)
pay(ali,200)
pay(app,1000)
# pay(app,1000)报错,原因是Applepay类没有实现这个方法

 通过接口类去断绝这种错误:

#接口类或者抽象类,起到规范作用(接口类或者抽象类中定义的方法,调用者必须规范实现),如果不规范实现,创建对象(实例化)即报错
from abc import abstractmethod,ABCMeta
class Payment(metaclass=ABCMeta):#必须指定元类ABCMeta
    @abstractmethod #必须加这个装饰器
    def pay(self,money):pass#抽象类或者接口类每定义一个方法都无需实现功能,但都需要在子类中一一实现



class Wechat(Payment):
    def pay(self,money):#只有在子类才能实现pay方法
        print('支付%s成功'%money)

class Alipay(Payment):
    def pay(self,money):#只有在子类才能实现pay方法
        print('支付%s成功'%money)

class Applepay(Payment):
    def zhifu(self,money):
        print('支付%s成功'%money)

def pay(payment,money):
    payment.pay(money)

wechat = Wechat()
ali = Alipay()
app = Applepay()#创建对象即报错,不需要等调用才会报错

 

接口类的多继承:

# 假设有动物:天鹅,老虎,鳄鱼,猫,根据水陆空,把他们分为三栖动物,二栖动物,单栖动物,我们把会飞的,会走的,会游的分别作为接口类,
# 而对应的动物类则分为三栖类,两栖类和单栖类,天鹅、老虎等则为对象
from abc import abstractmethod,ABCMeta
class Fly_animal(metaclass=ABCMeta):
    @abstractmethod
    def fly(self):pass
class Walk_animal(metaclass=ABCMeta):
    @abstractmethod
    def walk(self): pass
class Swim_animal(metaclass=ABCMeta):
    @abstractmethod
    def swim(self): pass

class Three_animals(Fly_animal,Walk_animal,Swim_animal):
    def fly(self):
        print('我会在天上飞')
    def walk(self):
        print('还会在陆地上走')
    def swim(self):
        print('还会在水里游泳')

class Two__animals(Walk_animal,Swim_animal):
    def walk(self):
        print('我会在陆地上走')
    def swim(self):
        print('还会在水里游泳')

class Single_animals(Walk_animal):
    def walk(self):
        print('我只生活在陆地')

tiger = Two__animals()
tiger.walk()
tiger.swim()

cats = Single_animals()
cats.walk()

 

抽象类:python原生支持,一般情况下单继承,抽象类中可以实现一些方法

#抽象类:把一堆类中相同的内容抽取出来,内容包括数据属性和函数属性。
# 比如有猪、小狗、牛,他们共同的特点是都有四条腿,都会游泳,四条腿是共同的属性,游泳则是共同的方法,我们则把他们相同的属性抽取出来当做一个抽象类
from abc import abstractmethod,ABCMeta
class Animal(metaclass=ABCMeta):
    leg = 4
    @abstractmethod
    def swim(self):pass

class Pig(Animal):
    def swim(self):
        print('我会游泳')

class Dog(Animal):
    def bite(self):
        print('我会咬人')

    def swim(self):
        print('我会游泳')

class Cow(Animal):
    def swim(self):
        print('我会游泳')

pig = Pig()
dog = Dog()
cow = Cow()
print(pig.leg)
print(dog.leg)
print(cow.leg)

dog.bite()
dog.swim()
cow.swim()
pig.swim()

 总结:Java的抽象类和接口类在python当中体现的并不明显,抽象类把一堆类中相同的内容抽取出来,内容包括数据属性和函数属性,实现规范。而接口类需要通过调用模块才能使用,接口类中的任何方法都只是一种规范,具体的功能需要子类实现,接口类可以多继承,但是继承接口类里的方法需要在子类里一一实现

posted @ 2019-09-05 18:40  aikell  阅读(253)  评论(0编辑  收藏  举报