• python类接口和抽象超类


    1 python类接口和抽象超类

    1.1 导入模块执行class语句

    python导入模块时会执行class语句及主体内的顶层语句。

    示例

    # test.py
    class MyClass:
        print('MyClass')
    # cmd执行下面语句
    E:\documents\F盘>python
    >>> import test
    MyClass
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7

    1.2 pytho类接口技术

    python类接口技术通过继承实现。

    # test.py
    class Super:
        '''定义一个超类。
        定义一个method方法。
        定义一个delegate方法,方法内调用子类定义的action方法。
        '''
        def method(self):
            print('in Super.method')
        def delegate(self):
            '''调用子类定义的action'''
            self.action()
        
    class Inheritor(Super):pass
    
    class Replacer(Super):
        '''定义 Replacer 继承 Super
        替换超类的 method 方法
        '''
        def method(self):
            print('in Replacer.method')
    
    class Extender(Super):
        '''定义 Extender 继承 Super
        调用超类的 method 方法, 并且进行扩展
        '''
        def method(self):
            print('Begin Extender.method')
            Super.method(self)
            print('End Extender.method')
            
    class Provider(Super):
        '''定义 Provider 继承 Super
        实现超类 delegate 内调用的 action 方法
        '''
        def action(self):
            print('in Provider.action')
            
    if __name__ == '__main__':
        for cls in (Inheritor,Replacer,Extender,Provider):
            print('\n{}....'.format(cls.__name__))
            cls().method()
            
        print('\nProvider')
        p = Provider()
        p.delegate()
     
    ''' 运行结果
    
    E:\documents\F盘>python test.py
    
    Inheritor....
    in Super.method
    
    Replacer....
    in Replacer.method
    
    Extender....
    Begin Extender.method
    in Super.method
    End Extender.method
    
    Provider....
    in Super.method
    
    Provider
    in Provider.action
    '''
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
    • 34
    • 35
    • 36
    • 37
    • 38
    • 39
    • 40
    • 41
    • 42
    • 43
    • 44
    • 45
    • 46
    • 47
    • 48
    • 49
    • 50
    • 51
    • 52
    • 53
    • 54
    • 55
    • 56
    • 57
    • 58
    • 59
    • 60
    • 61
    • 62
    • 63
    • 64
    • 65
    • 66
    • 67

    1.3 python抽象超类

    python类的部分行为由子类提供,则为抽象超类。

    1.3.1 调用方法时触发提示

    显式要求子类必须实现抽象超类的方法:

    (1) 方法一,在超类方法用assert False

    (2) 方法二,在超类方法用 raise NotImplementedError

    未实现,则在实例调用方法时触发报错提示。

    子类和超类都未提供方法,报 has no attribute

    >>> class AbsSuper:
        def delegate(self):
            self.action()
            
    >>> class Provider(AbsSuper):pass
    >>> p=Provider()
    >>> p.delegate()
    Traceback (most recent call last):
      File "", line 1, in <module>
        p.delegate()
      File "", line 3, in delegate
        self.action()
    AttributeError: 'Provider' object has no attribute 'action'
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13

    在超类方法用assert False

    >>> class AbsSuper:
        def delegate(self):
            self.action()
        def action(self):
            assert False,'子类必须定义 action'
    
            
    >>> class Provider(AbsSuper):pass
    
    >>> Provider().delegate()
    Traceback (most recent call last):
      File "", line 1, in <module>
        Provider().delegate()
      File "", line 3, in delegate
        self.action()
      File "", line 5, in action
        assert False,'子类必须定义 action'
    AssertionError: 子类必须定义 action
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18

    在超类方法用raise NotImplementedError

    >>> class AbsSuper:
        def delegate(self):
            self.action()
        def action(self):
            raise NotImplementedError('子类必须定义 action')
    >>> class Provider(AbsSuper):pass
    
    >>> Provider().delegate()
    Traceback (most recent call last):
      File "", line 1, in <module>
        Provider().delegate()
      File "", line 3, in delegate
        self.action()
      File "", line 5, in action
        raise NotImplementedError('子类必须定义 action')
    NotImplementedError: 子类必须定义 action
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16

    1.3.2 创建实例时触发提示

    (1) 带有@abstractmethod修饰的方法为抽象方法。

    (2) 带有抽象方法的类不能进行实例化。

    (3) 超类有抽象方法时,子类必须重写超类的抽象方法。

    (4) 未重写,则创建实例时触发报错提示。

    抽象方法定义:

    (1) python3:超类头部括号送metaclass**=**ABCMeta。

    (2) python2:超类主体定义__metaclass__**=**ABCMeta。

    (3) 用@abstractmethod修饰方法。

    python3示例

    >>> from abc import ABCMeta,abstractmethod
    >>> class MySuper(metaclass=ABCMeta):
        def delegate(self):
            self.action()
        # @abstractmethod 为抽象方法,子类必须重写
        @abstractmethod
        def action(self):
            pass  # 抽象方法在父类通常留空,用pass进行占位
    
        
    >>> ms=MySuper()
    Traceback (most recent call last):
      File "", line 1, in <module>
        ms=MySuper()
    # 不能实例化有抽象方法的父类
    TypeError: Can't instantiate abstract class MySuper with abstract methods action
    >>> class MySub(MySuper):pass
    
    >>> sub=MySub()
    Traceback (most recent call last):
      File "", line 1, in <module>
        sub=MySub()
    # 子类未实现父类抽象方法,不能实例化子类
    TypeError: Can't instantiate abstract class MySub with abstract methods action
    
    >>> class MySub(MySuper):
        def action(self):
            print('梯阅线条')
    
            
    >>> sub=MySub()
    >>> sub.delegate()
    梯阅线条
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28
    • 29
    • 30
    • 31
    • 32
    • 33
  • 相关阅读:
    Python绘图系统25:新增8种绘图函数
    【红外图像增强】基于引力和侧向抑制网络的红外图像增强模型(Matlab代码实现)
    zabbix配置钉钉告警、和故障自愈
    对于计算机等级考试的建议
    RV1126笔记四十一:RV1126移植LIVE555
    2023第一届OPENAIGC开发者大赛圆满收官&获奖名单公示
    DOM系列之classList属性
    写个计算器
    【Linux】基本指令(一)
    04_SpingBoot 前端使用JSP
  • 原文地址:https://blog.csdn.net/sinat_34735632/article/details/134431358