ABC,Abstract Base Class(抽象基类),主要定义了基本类和最基本的抽象方法,可以为子类定义共有的API,不需要具体实现。相当于是Java中的接口或者是抽象类。
抽象基类可以不实现具体的方法(当然也可以实现,只不过子类如果想调用抽象基类中定义的方法需要使用super())而是将其留给派生类实现。
抽象基类提供了逻辑和实现解耦的能力,即在不同的模块中通过抽象基类来调用,可以用最精简的方式展示出代码之间的逻辑关系,让模块之间的依赖清晰简单。同时,一个抽象类可以有多个实现,让系统的运转更加灵活。而针对抽象类的编程,让每个人可以关注当前抽象类,只关注其方法和描述,而不需要考虑过多的其他逻辑,这对协同开发有很大意义。极简版的抽象类实现,也让代码可读性更高。
抽象基类的使用:
1:直接继承
直接继承抽象基类的子类就没有这么灵活,抽象基类中可以声明”抽象方法“和“抽象属性”,只有完全覆写(实现)了抽象基类中的“抽象”内容后,才能被实例化,而虚拟子类则不受此影响。
2:虚拟子类
将其他的类”注册“到抽象基类下当虚拟子类(调用register方法),虚拟子类的好处是你实现的第三方子类不需要直接继承自基类,可以实现抽象基类中的部分API接口,也可以根本不实现,但是issubclass(), issubinstance()进行判断时仍然返回真值。
Python 对于ABC的支持模块是abc模块,定义了一个特殊的metaclass:ABCMeta 还有一些装饰器:@abstractmethod 和 @abstarctproperty 。abc.ABCMeta 用于在Python程序中创建抽象基类。而抽象基类如果想要声明“抽象方法”,可以使用 @abstractmethod ,如果想声明“抽象属性”,可以使用 @abstractproperty 。
为了解决Python2&3的兼容问题,需要引入six模块,该模块中有一个针对类的装饰器 @six.add_metaclass(MetaClass) 可以为两个版本的Python类方便地添加metaclass
通用做法。
@six.add_metaclass(MetaClass) 的作用是在不同版本的Python之间提供一个优雅的声明类的metaclass的手段,事实上不用它也可以,只是使用了它代码更为整洁明了。
import six
@six.add_metaclass(Meta)
class MyClass(object):
pass
在Python 3 等价于
import six
class MyClass(object, metaclass = Meta):
pass
在Python 2.x (x >= 6)中等价于
import six
class MyClass(object):
__metaclass__ = Meta
pass
或者直接调用装饰器,
这里也能看出来装饰器就是个方法包装而已。
import six
class MyClass(object):
pass
MyClass  = six.add_metaclass(Meta)(MyClass)
实例:
import abc
import six
@six.add_metaclass(abc.ABCMeta)
class BaseClass(object):
@abc.abstractmethod
def func_a(self, data):
"""
an abstract method need to be implemented
"""
@abc.abstractmethod
def func_b(self, data):
"""
another abstract method need to be implemented
"""
class SubclassImpl(BaseClass):
def func_a(self, data):
print("Overriding func_a, " + str(data))
@staticmethod
def func_d(self, data):
print(type(self) + str(data))
class RegisteredImpl(object):
@staticmethod
def func_c(data):
print("Method in third-party class, " + str(data))
BaseClass.register(RegisteredImpl)
if __name__ == '__main__':
for subclass in BaseClass.__subclasses__():
print("subclass of BaseClass: " + subclass.__name__)
print("subclass do not contains RegisteredImpl")
print("-----------------------------------------------")
print("RegisteredImpl is subclass: " + str(issubclass(RegisteredImpl, BaseClass)))
print("RegisteredImpl object  is instance: " + str(isinstance(RegisteredImpl(), BaseClass)))
print("SubclassImpl is subclass: " + str(issubclass(SubclassImpl, BaseClass)))
print("-----------------------------------------------")
obj1 = RegisteredImpl()
obj1.func_c("RegisteredImpl new object OK!")
print("-----------------------------------------------")
obj2 = SubclassImpl()  #由于没有实例化所有的方法,所以这里会报错 Can't instantiate abstract class SubclassImpl with abstract methods func_b
obj2.func_a("It's right!")
结果如下:
subclass of BaseClass: SubclassImpl
subclass do not contains RegisteredImpl
-----------------------------------------------
RegisteredImpl is subclass: True
RegisteredImpl object  is instance: True
SubclassImpl is subclass: True
-----------------------------------------------
Method in third-party class, RegisteredImpl new object OK!
-----------------------------------------------
Traceback (most recent call last):
File "/Users/wangqi/Git/Python/scrapy_crawler_learn/test/ABCTest.py", line 51, in <module>
obj2 = SubclassImpl()  #由于没有实例化所有的方法,所以这里会报错 Can't instantiate abstract class SubclassImpl with abstract methods func_b
TypeError: Can't instantiate abstract class SubclassImpl with abstract methods func_b

1. #我们去检查某个类是否有某种方法
class Company(object):
    def __init__(self, employee_list):
        self.employee = employee_list

def __len__(self):
        return len(self.employee)

com = Company(["bobby1","bobby2"])
print(hasattr(com, "__len__"))

class A:
    pass

class B:
    pass

2.  #我们在某些情况之下希望判定某个对象的类型
from collections.abc import Sized
isinstance(com, Sized)

b = B()
print(isinstance(b, A))
# print(len(com))

3. 
#我们需要强制某个子类必须实现某些方法
#实现了一个web框架,集成cache(redis, cache, memorychache)
#需要设计一个抽象基类, 指定子类必须实现某些方法

#如何去模拟一个抽象基类

import abc
from collections.abc import *

class CacheBase(metaclass=abc.ABCMeta):
    @abc.abstractmethod
    def get(self, key):
        pass

@abc.abstractmethod
    def set(self, key, value):
        pass
# class CacheBase():
#     def get(self, key):
#         raise NotImplementedError
#     def set(self, key, value):
#         raise NotImplementedError
#
class RedisCache(CacheBase):
    def set(self, key, value):
        pass

# redis_cache = RedisCache()
# redis_cache.set("key", "value")

Python高级:了解Python ABC(抽象基类)及 应用场景相关推荐

  1. python abc模块_3-2 抽象基类abc模块

    abc ---- Abstract base class 何为抽象基类: 类比JAVA: 可以当作是JAVA中的接口,在JAVA里面它是无法实现多继承的,JAVA只能继承一个类,但是JAVA可以继承多 ...

  2. Python:抽象基类(abc模块)

    抽象基类(abc模块) 介绍 白话理解 实用场景 介绍 该模块提供了一个元类 ABCMeta,可以用来定义抽象类,另外还提供一个工具类 ABC,可以用它以继承的方式定义抽象基类. 装饰器以" ...

  3. Python学习笔记28:从协议到抽象基类

    Python学习笔记28:从协议到抽象基类 今后本系列笔记的示例代码都将存放在Github项目:https://github.com/icexmoon/python-learning-notes 在P ...

  4. Python ABC(抽象基类)

    轉自:https://blog.csdn.net/qijiqiguai/article/details/77269839 ABC(Abstract Base Class抽象基类)主要定义了不需要具体实 ...

  5. python之抽象基类

    抽象基类特点 1.不能够实例化 2.在这个基础的类中设定一些抽象的方法,所有继承这个抽象基类的类必须覆盖这个抽象基类里面的方法 思考 既然python中有鸭子类型,为什么还要使用抽象基类? 一是我们在 ...

  6. python抽象基类的作用_Python:多态、鸭子模型和抽象基类

    1. 多态 什么是多态 -- 多态,指的是一种事务具有多种形态: -- python是一种动态语言,默认支持多态,同一个方法 调用 不同的类对象 ,执行的 结果各不相同: 多态实现 -- 继承:不同子 ...

  7. python虚函数_Python进阶话题杂谈(十三)纯虚函数与抽象基类

    纯虚函数与抽象类都是Python面向对象中重要的编程范式,用于对继承类做强制性接口实现约定. abc模块包含了一系列与抽象基类与纯虚函数相关的方法.Python中通过修改元类进行抽象基类的设定.这里P ...

  8. python类方法和实例方法syntax errors_《Fluent Python》CH.11_面向对象_接口:从协议到抽象基类...

    主要内容 首先,本章说明抽象基类的常见用途:实现接口时作为超类使用 说明抽象基类如何检查具体子类是否符合接口定义,以及如何使 用注册机制声明一个类实现了某个接口,而不进行子类化操作 最后, 说明如何让 ...

  9. python 基类是什么_python之抽象基类

    python之抽象基类 抽象基类,在这个类中定义一些方法,所有继承这个类的类必须实现这个方法,并且这个类不能被实例化, 使用抽象基类的情况: 1.某些情况下希望判断某个对象的类型 2.强制子类必须实现 ...

最新文章

  1. 网站SEO更新时选择适当的时间点有什么好处?
  2. linux命令行ps1变量_Linux下SHELL的PS1变量简介
  3. python 将图片旋转多个角度_【技术】把你的朋友变成表情包?Python:So easy
  4. Python面向对象学习 1 (什么是面向对象,面向对象的应用场景,待更新)
  5. MySQL Innodb存储引擎使用B+树做索引的优点
  6. dz论坛服务器技术支持,服务器更换 升级 dz论坛首页 dz其他页面打开为空白解决方法...
  7. apache2.4 php5.6.30,php5.6.3 + apache2.4.25 安装配置
  8. c++ gzip java.util.zip.gzip_java.util.zip.GZIPInputStream.close()方法示例
  9. 读论文看到的好的英文词句表达
  10. VBA之正则表达式(30)-- 提取机构代码
  11. 原创 C++应用程序在Windows下的编译、链接:第二部分COFF/PE文件结构
  12. 从linaro下载安装二进制文件安装交叉编译工具
  13. linkinfo() 函数
  14. 网页设计图片向上浮动_网页设计与制作(网页设计、制作与美化)
  15. 武大三行情书第一名---《螃蟹在剥我的壳》
  16. redis keys命令,生产环境慎用,最好屏蔽掉
  17. 最大值最小值计算机一级,Excel2019中突出数据最大值和最小值的方法详解
  18. 怎么样在家拍出好看的证件照?标准证件照拍摄技巧分享
  19. Windows10重装设置(个人)
  20. 【图像几何】基于傅里叶+DCT图像变换matlab代码

热门文章

  1. 如果只能从市面上的Python入门书中选择一本送给你,那我一定会选这本……
  2. 普林斯顿大学算法公开课笔记
  3. 思科网络安全 第十一章测验答案
  4. 无敌破坏王-高清在线观看
  5. 计算机哪所民办学校好,哪所民办高校计算机软件方面好?
  6. 1024Byte(字节)=1KB
  7. 设计模式 之 结构型模式
  8. 任天堂游戏服务器系统,买个服务器当电脑主机如何确保买到新版任天堂Switch游戏主机?...
  9. android webdav客户端,WebDAV精灵
  10. PHP毕业设计源代码剧影评|剧评影评系统