通过 Python 理解 Mixin 概念
Mixin 的概念
Mixin 即 Mix-in
,常被译为“混入”,是一种编程模式,在 Python 等面向对象语言中,通常它是实现了某种功能单元的类,用于被其他子类继承,将功能组合到子类中。
利用 Python 的多重继承,子类可以继承不同功能的 Mixin 类,按需动态组合使用。
当多个类都实现了同一种功能时,这时应该考虑将该功能抽离成 Mixin 类。
举个例子
定义一个简单的类:
class Person:
def __init__(self, name, gender, age):
self.name = name
self.gender = gender
self.age = age
我们可以通过调用实例属性的方式来访问:
p = Person("小陈", "男", 18)
print(p.name) # "小陈"
然后我们定义一个 Mixin 类:
class MappingMixin:
def __getitem__(self, key):
return self.__dict__.get(key)
def __setitem__(self, key, value):
return self.__dict__.set(key, value)
这个类可以让子类拥有像 dict 一样调用属性的功能
我们将这个 Mixin 加入到 Person 类中:
class Person(MappingMixin):
def __init__(self, name, gender, age):
self.name = name
self.gender = gender
self.age = age
现在 Person 拥有另一种调用属性方式了:
p = Person("小陈", "男", 18)
print(p['name']) # "小陈"
print(p['age']) # 18
再定义一个 Mixin 类,这个类实现了 __repr__
方法,能自动将属性与值拼接成字符串:
class ReprMixin:
def __repr__(self):
s = self.__class__.__name__ + '('
for k, v in self.__dict__.items():
if not k.startswith('_'):
s += '{}={}, '.format(k, v)
s = s.rstrip(', ') + ')' # 将最后一个逗号和空格换成括号
return s
利用 Python 的特性,一个类可以继承多个父类:
class Person(MappingMixin, ReprMixin):
def __init__(self, name, gender, age):
self.name = name
self.gender = gender
self.age = age
这样这个子类混入了两种功能:
p = Person("小陈", "男", 18)
print(p['name']) # "小陈"
print(p) # Person(name=小陈, gender=男, age=18)
总结
Mixin 实质上是利用语言特性,可以把它看作一种特殊的多重继承,所以它并不是 Python 独享,只要支持多重继承或者类似特性的都可以使用,比如 Ruby 中 include 语法,Vue 等前端领域也有 Mixin 的概念。
但 Mixin 终归不属于语言的语法,为了代码的可读性和可维护性,定义和使用 Mixin 类应该遵循几个原则:
- Mixin 实现的功能需要是通用的,并且是单一的,比如上例中两个 Mixin 类都适用于大部分子类,每个 Mixin 只实现一种功能,可按需继承。
- Mixin 只用于拓展子类的功能,不能影响子类的主要功能,子类也不能依赖 Mixin。比如上例中
Person
继承不同的 Mixin 只是增加了一些功能,并不影响自身的主要功能。如果是依赖关系,则是真正的基类,不应该用 Mixin 命名。 - Mixin 类自身不能进行实例化,仅用于被子类继承。
本文属于原创,首发于微信公众号「面向人生编程」,如需转载请后台留言。
关注后回复以下信息获取更多资源
回复【资料】获取 Python / Java 等学习资源
回复【插件】获取爬虫常用的 Chrome 插件
回复【知乎】获取最新知乎模拟登录
通过 Python 理解 Mixin 概念的更多相关文章
- 对于新手来说,Python 中有哪些难以理解的概念?
老手都是从新手一路过来的,提起Python中难以理解的概念,可能很多人对于Python变量赋值的机制有些疑惑,不过对于习惯于求根究底的程序员,只有深入理解了某个事物本质,掌握了它的客观规律,才能得心应 ...
- RxSwift 系列(九) -- 那些难以理解的概念
前言 看完本系列前面几篇之后,估计大家也还是有点懵逼,本系列前八篇也都是参考RxSwift官方文档和一些概念做的解读.上几篇文章概念性的东西有点多,一时也是很难全部记住,大家脑子里面知道有这么个概念就 ...
- 用 Python 理解 Web 并发模型
用 Python 理解 Web 并发模型 http://www.jianshu.com/users/1b1fde012122/latest_articles 来源:MountainKing 链接: ...
- python用法——Mixin
在读werkzeug和flask的源码中,经常能遇到类名中有mixin这个东西.这个东西的用法让我想到了java中的接口名有able的用法.今天我就来看了看这个mixin是什么东西. 学习了pytho ...
- python异常(概念、捕获、传递、抛出)
异常 目标 异常的概念 捕获异常 异常的传递 抛出异常 01. 异常的概念 程序在运行时,如果 Python 解释器 遇到 到一个错误,会停止程序的执行,并且提示一些错误信息,这就是 异常 程序停止执 ...
- 关于Python的Mixin模式
转自:http://www.bjhee.com/python-mixin.html 像C或C++这类语言都支持多重继承,一个子类可以有多个父类,这样的设计常被人诟病.因为继承应该是个”is-a”关系. ...
- 【转载】关于Python的Mixin模式
本博按: mixin是看起来是多继承的一种,但是,这种继承并不作为父类存在,而是增加功能到子类中. 像C或C++这类语言都支持多重继承,一个子类可以有多个父类,这样的设计常被人诟病.因为继承应该是个” ...
- Python 字典Dict概念和操作
# 字典概念:无序的, 可变的键值对集合 # 定义 # 方式1 # {key: value, key: value...} # 例如 # {"name": "xin&qu ...
- 以python理解Linux的IO多路复用,select、poll、epoll
题外话 之前在看Unix环境高级编程的时候,看完高级IO那一章,感觉自己萌萌哒,0.0 ,有点囫囵吞枣的感觉,之后翻了几篇博客,从纯系统的角度理解,稍微有了点概念,以这两篇为例,可以以后参考: htt ...
随机推荐
- 在虚拟机上的关于NFS网络文件系统
小知识: NFS(Network Files System)即网络文件系统,NFS文件系统协议允许网络中的主机通过TCP/IP协议进行资源共享,NFS客户端可以像使用本地资源一样读写远端NFS服务端的 ...
- shell 队列实现线程并发控制
需求:并发检测1000台web服务器状态(或者并发为1000台web服务器分发文件等)如何用shell实现? 方案一:(这应该是大多数人都第一时间想到的方法吧) 思路:一个for循环1000次,顺序执 ...
- Unity3-各个内置面板,对象说明
*在Inspector面板中,是表示每个物体(诸如摄像机,圆柱,正方体)的组件. 组件包含: 1.Transform,在第一节当中,可以用于变换物体的位置.每个物体对象都有. 2.cube,网格,对于 ...
- 分手是祝愿:dp
Description Zeit und Raum trennen dich und mich. 时空将你我分开. B 君在玩一个游戏,这个游戏n个灯和n个开关组成,给定这n个灯的初始状态,下标为从1 ...
- NOIP模拟12
也算是最近几次比较水的一次吧. 考试时看T1像个打表找规律的题,扔了,去看T2,带修莫队??不会,完戏.看了T3,我决定还是去看T1. 看着T1,我突然发现T2是个大水题:主席树就行,不带修,修改时只 ...
- 通过IDEA快速定位和排除依赖冲突
前言 我们程序员在开发的时候经常会遇到各种各样的 BUG 问题,其中大部分是业务逻辑异常,还有一些是代码书写不规范造成的异常例如:NullPointException(NPE),IndexOutOfB ...
- Java自动化测试框架-10 - TestNG之测试结果篇
1.-测试结果 1.1-成功,失败和断言 测试被认为是成功的,如果它不引发任何异常完成,还是它扔的预期异常(请参阅文档expectedExceptions属性上找到的@Test注释). 您的测试方法通 ...
- Java I/O系统学习系列五:Java序列化机制
在Java的世界里,创建好对象之后,只要需要,对象是可以长驻内存,但是在程序终止时,所有对象还是会被销毁.这其实很合理,但是即使合理也不一定能满足所有场景,仍然存在着一些情况,需要能够在程序不运行的情 ...
- win+L键失灵了怎么办?
win+L组合键是比较常用的锁屏快捷键组合,一直用的好好的今天发现突然失灵. 百度大部分方法是改注册表的值,然而对我来说没有用. 最后,才搜到一个帖子说是 win键被锁住了. [解决方法]: Fn+w ...
- 洛谷 pP2146 [NOI2015]软件包管理器
题目的传送门 题目描述 Linux用户和OSX用户一定对软件包管理器不会陌生.通过软件包管理器,你可以通过一行命令安装某一个软件包,然后软件包管理器会帮助你从软件源下载软件包,同时自动解决所有的依赖( ...