魔法函数
引言
- 魔法函数是
Python
中定义的,以__
开头,__
结尾,形如__func__()
的函数,一般使用已经存在的魔法函数即可。 - 使用这样一些函数,可以让我们自定义的类有更加强大的特性。
- 魔法函数是隐式调用的,不需要我们显示调用。
class Language(object):
def __init__(self, language_list):
self.lans = language_list
# 如果要遍历所有的语言,可以:
language = Language(["Python", "C", "Lisp"])
for lan in language.lans:
print(lan)
# result:
# Python
# C
# Lisp
用魔法函数也可实现上面的功能,而且使用起来会更加简洁。
class Language(object):
# 没错,这也是一个魔法函数,现在先不关注它
def __init__(self, language_list):
self.lans = language_list
# 定义这样一个魔法函数
def __getitem__(self, item):
return self.lans[item]
language = Language(["Python", "C", "Lisp"])
for lan in language:
print(lan)
# result:
# Python
# C
# Lisp
魔法函数对Python的影响
- 魔法函数不属于定义它的那个类,只是增强了类的一些功能。
- 类中实现了特定的魔法函数之后,会获得一些奇特的功能,某些操作会变得特别简单。
- 我们可以采用实现魔法函数来灵活地设计我们需要的类。
常用魔法函数
后续学习会介绍一部分,这里了解即可。
非数学运算
字符串表示
__repr__()
__str__()
集合、序列
__len__()
__getitem__()
__setitem__()
__delitem__()
__contains__()
迭代相关
__iter__()
__next__()
可调用
__call__()
with上下文管理器
__enter__()
__exit__()
数值转换
__abs__()
__bool__()
__int__()
__float__()
__hash__()
__index__()
元类相关
__new__()
__init__()
属性相关
-
__getattr__()
,__setattr__()
-
__getattribute__()
,__setattribute__()
__dir__()
属性描述符
-
__get__()
,__set__()
,__delete__()
携程
-
__await__()
,__aiter__()
,__anext__()
,__aenter__()
,__aexit__()
数学运算
看一个例子就行了,因为:
- 运算方式复杂
- 实际应用不多
# 实现一个二维向量的加法计算
class Vector(object):
def __init__(self, x, y):
self.x = x
self.y = y
# 定义了向量对象能够直接相加的魔法函数
def __add__(self, v):
res_v = Vector(self.x + v.x, self.y + v.y)
return res_v
# 如果你熟悉 java ,这个魔法函数有些类似于 toString()
def __str__(self):
return "x: {0}, y: {1}".format(self.x, self.y)
first_vector = Vector(1, 2)
second_vector = Vector(3, 4)
print(first_vector + second_vector)
# result:
# x: 4, y: 6
以len()为例
引言
-
len()
函数可以返回一个序列的长度 - 首先该类型要定义了
__len__()
方法
原理
当我们使用len()
函数获取一些内置对象(list, tuple, set...)的长度时,性能会非常高,因为这些内置对象使用C
语言实现的,同时该方法并未对内置对象进行遍历获得长度,而是内置对象维护了一个长度属性,调用方法后,直接进行属性值的读取即可。
结论
- 某些方法并未我们想象中的那么简单,内部实现时会做很多优化。
- 尽量使用
Python
的内置对象,和内置的一些函数,提高效率。
小结
魔法函数使得自定义的类型会具有神奇的功能,让我们可以设计更加灵活的类型,它将我们自定义的类型和一些内建类型建立起了关联,明白了更加底层的一些细节,这里只为后面的的深入学习做了一个铺垫,具体的魔法函数会在后面的部分得到体现。
网友评论