python:基于super()函数初始化
super() 函数的一种常见用途就是继承父类时,调用父类方法,能确保父类被正常初始化。
通常在继承类中我们可以看到直接调用父类中的方法,就像下面这样:
class Base:
def __init__(self):
print("Base = __init__")
class A(Base):
def __init__(self):
Base.__init__(self)
print("A = __init__")
尽管在继承类中可以这样直接调用父类使用,但是在多继承中就会出现多次调用的情况。比如下面这个例子:
class Base:
def __init__(self):
print("Base = __init__")
class A(Base):
def __init__(self):
Base.__init__(self)
print("A = __init__")
class B(Base):
def __init__(self):
Base.__init__(self)
print("B = __init__")
class C(A, B):
def __init__(self):
A.__init__(self)
B.__init__(self)
print("C = __init__")
if __name__ == '__main__':
c = C()
print(c)
上面的代码运行后,会发现 “ Base = init ” 被调用了两次。就像下面这样:
Base = __init__
A = __init__
Base = __init__
B = __init__
C = __init__
<__main__.C object at 0x000001D51899BE50>
Process finished with exit code 0
当然这样调用并不是不可以,也没有什么害处。但也不排除出现问题的可能性,所以尽量规范去调用,将代码修改为使用super()后,那么一切工作就能正常工作了(官方推荐使用 “ super().int() ” 调用):
class Base:
def __init__(self):
print("Base = __init__")
class A(Base):
def __init__(self):
super().__init__()
print("A = __init__")
class B(Base):
def __init__(self):
super().__init__()
print("B = __init__")
class C(A, B):
def __init__(self):
super().__init__()
print("C = __init__")
if __name__ == '__main__':
c = C()
print(c)
代码修改为super()调用并运行后,就会发现每个__init__()只调用了一次(这种调用是规范的,也是官方推荐的)。就像下面这样:
Base = __init__
B = __init__
A = __init__
C = __init__
<__main__.C object at 0x000001B462C9A6B0>
为什么两种调用产生的结果会不一致呢?
首先python的继承时,会计算出一个解析顺序的MRO的只读列表。就像下面这样:
if __name__ == '__main__':
print(C.mro())
# 运行结果
[<class '__main__.C'>, <class '__main__.A'>, <class '__main__.B'>, <class '__main__.Base'>, <class 'object'>]
Process finished with exit code 0
在MRO列表中,可看到继承的顺序是先自己本身,继承了两个类的时候是先左后右,如果父类还有继承则再继续找父类的父类,最后再找到原始基类(object),这也是继承运行的执行顺序。
而“ Base = init ” 被调用了两次的原因是因为A类中继承Base父类,B类中也继承了Base父类,然后C又继承了A、B父类,这个时候运行C类时,C在初始化时分别调用了“ A.init(self) ”和“ B.init(self) ”,最后结果就必然会产生Base基类被多次调用的效果了。
当修改为“ super().init() ” 时,没有产生多次调用的原因则是每个类在初始化时都进行了super()的重新定义后的方法覆盖(也就是重写),自然就不会出现多次调用的效果了。
今天先聊到这里吧,以上总结或许能帮助到你,或许帮助不到你,但还是希望能帮助到你,如有疑问、歧义,直接私信留言会及时修正发布;非常期待你的一键④连【 赞赏、点赞、在看、分享】哟,谢谢!
未完成,待续……
我推荐一个【Python自动化测试交流群:746506216】,大家可以一起探讨交流软件测试,共同学习软件测试技术、面试等软件测试方方面面,助你快速进阶Python自动化测试/测试开发,走向高薪之路。
喜欢软件测试的小伙伴们,如果我的博客对你有帮助、如果你喜欢我的博客内容,请 “点赞” “评论” “收藏” 一 键三连哦!
相关文章
- python随机产生100000个数计算满足条件的比例
- python学习系列-3-求知讲堂python
- Python任意参数的数量/预习课python基础
- Python变量/运算符/函数/模块/string
- 如何快速学习python,学好python?能通过Python赚到的第一笔钱,有哪些经验可以分享吗?
- 2023版Python零基础入门基础教程(非常详细)
- python:基于super()函数初始化
- python通过tcp收发数据
- python 中numpy中函数hstack用法和作用
- python之函数用法id(),了解即可
- Python有哪些就业方向 你知道Python的优势吗
- 『 迷你教程 』Python中的函数式编程全方法详解
- Python 教程之如何使用 matplotlib 在 python 中绘制数学函数
- Python基础入门-实现猜数字小游戏
- 《从问题到程序:用Python学编程和计算》——2.3 内置函数和数学函数包
- Python函数
- python变量作用域,函数与传参
- python之enumerate函数:获取列表中每个元素的索引和值
- Python学习---基础函数的学习
- python函数之hstack函数--用于将两数组或矩阵合并
- Python 基础 之 python 协程知识点整理,并实现一个简单 gevent 的协程并发图片下载的应用
- Sublime Text 3 插件安装、搭建Python、Java开发环境
- Python的数据库mongoDB的入门操作
- 【python】postgresql插入数据后conn与cursor提交与关闭问题
- python下的符号函数
- caffe添加自己编写的Python层
- python lambda函数 匿名函数