当用Python定义一个类的时候,其实有一些固定的方法,这些方法是固定的,当然程序员是可以根据自己的需求去更改。

每次我在使用这些方法的时候,我还需要去自己去查,很麻烦,因此我打算总结一套全部的内置方法。

关于对象周期的方法

这部分其实主要就是构造方法和析构方法。

构造方法

  • __new__(cls,[...)

    或许大部分人认为构造方法为__init__(),其实在这之前还有一个方法,这个方法在对象实例化的时候调用,而且比__init__()执行的时间还要早,但不经常用,除非特殊情况。

  • __init__(self,[...])

    这就很常见了,一般用作初始化,注意,形参的参数是决定实例化的时候传进来的参数,所以这很重要,一般都会自己去重写。

析构方法

  • __del__(self)

    主要是在销毁的时候会调用这个方法,但是需要注意的是,当Python解释器退出但对象仍然存活的时候, __del__()并不会 执行。 所以养成一个手工清理的好习惯是很重要的,比如及时关闭连接。

操作符

有些方法可以根据操作符执行,利用好的话可以玩出很多花样。

比较运算符

  • __cmp__(self, other)

    它上定义了所有比较操作符的行为(<,==,!=,等等),当使用这些运算符的时候就会调用,但其实并不常用,因为不方便,不能判断使用的是哪种运算符。

  • __eq__(self, other)

    定义等于操作符(==)的行为。

  • __ne__(self, other)

    定义不等于操作符(!=)的行为。

  • __lt__(self, other)

    定义小于操作符(<)的行为。

  • __gt__(self, other)

    定义大于操作符(>)的行为。

  • __le__(self, other)

    定义小于等于操作符(<)的行为。

  • __ge__(self, other)

    定义大于等于操作符(>)的行为。

数值操作符

一元操作符

一元操作符只有一个操作符。

  • __pos__(self)

    实现取正操作,例如 +some_object。

  • __neg__(self)

    实现取负操作,例如 -some_object。

  • __abs__(self)

    实现内建绝对值函数 abs() 操作。

  • __invert__(self)

    实现取反操作符 ~。

  • __round__(self, n)

    实现内建函数 round() ,n 是近似小数点的位数。

  • __floor__(self)

    实现 math.floor() 函数,即向下取整。

  • __ceil__(self)

    实现 math.ceil() 函数,即向上取整。

  • __trunc__(self)

    实现 math.trunc() 函数,即距离零最近的整数。

二元运算符

也就是基本的算数运算符。

  • __add__(self, other)

    实现加法操作。

  • __sub__(self, other)

    实现减法操作。

  • __mul__(self, other)

    实现乘法操作。

  • __floordiv__(self, other)

    实现使用 // 操作符的整数除法。

  • __div__(self, other)

    实现使用 / 操作符的除法。

  • __truediv__(self, other)

    实现 _true_ 除法,这个函数只有使用from __future__ import division时才有作用。

  • __mod__(self, other)

    实现 % 取余操作。

  • __divmod__(self, other)

    实现 divmod 内建函数。

  • __pow__

    实现 ** 操作符。

  • __lshift__(self, other)

    实现左移位运算符 << 。

  • __rshift__(self, other)

    实现右移位运算符 >> 。

  • __and__(self, other)

    实现按位与运算符 & 。

  • __or__(self, other)

    实现按位或运算符 | 。

  • __xor__(self, other)

    实现按位异或运算符 ^ 。

反射运算符

  • radd__(self, other)

    实现反射加法操作。

  • rsub__(self, other)

    实现反射减法操作。

  • rmul__(self, other)

    实现反射乘法操作。

  • rfloordiv__(self, other)

    实现使用 // 操作符的整数反射除法。

  • rdiv__(self, other)

    实现使用 / 操作符的反射除法。

  • rtruediv__(self, other)

    实现 _true_ 反射除法,这个函数只有使用 from __future__ import division 时才有作用。

  • rmod__(self, other)

    实现 % 反射取余操作符。

  • rdivmod__(self, other)

    实现调用 divmod(other, self)divmod 内建函数的操作。

  • rpow__(self, other)

    实现 ** 反射操作符。

  • rlshift__(self, other)

    实现反射左移位运算符 << 的作用。

  • rshift__(self, other)

    实现反射右移位运算符 >> 的作用。

  • rand__(self, other)

    实现反射按位与运算符 & 。

  • ror__(self, other)

    实现反射按位或运算符 | 。

  • rxor__(self, other)

    实现反射按位异或运算符 ^ 。

增强赋值运算符

  • __iadd__(self, other)

    实现加法赋值操作。

  • __isub__(self, other)

    实现减法赋值操作。

  • __imul__(self, other)

    实现乘法赋值操作。

  • __ifloordiv__(self, other)

    实现使用 //= 操作符的整数除法赋值操作。

  • __idiv__(self, other)

    实现使用 /= 操作符的除法赋值操作。

  • __itruediv__(self, other)

    实现 _true_ 除法赋值操作,这个函数只有使用 from __future__ import division 时才有作用。

  • __imod__(self, other)

    实现 %= 取余赋值操作。

  • __ipow__(self, other)

    实现 **= 操作。

  • __ilshift__(self, other)

    实现左移位赋值运算符 <<= 。

  • __irshift__(self, other)

    实现右移位赋值运算符 >>= 。

  • __iand__(self, other)

    实现按位与运算符 &= 。

  • __ior__(self, other)

    实现按位或赋值运算符 | 。

  • __ixor__(self, other)

    实现按位异或赋值运算符 ^= 。

类型转换

  • __int__(self)

    实现到int的类型转换。

  • __long__(self)

    实现到long的类型转换。

  • __float__(self)

    实现到float的类型转换。

  • __complex__(self)

    实现到complex的类型转换。

  • __oct__(self)

    实现到八进制数的类型转换。

  • __hex__(self)

    实现到十六进制数的类型转换。

  • __index__(self)

    实现当对象用于切片表达式时到一个整数的类型转换。如果你定义了一个可能会用于切片操作的数值类型,你应该定义 __index__

  • __trunc__(self)

    当调用 math.trunc(self) 时调用该方法, __trunc__ 应该返回 self 截取到一个整数类型(通常是long类型)的值。

  • __coerce__(self)

    该方法用于实现混合模式算数运算,如果不能进行类型转换, __coerce__应该返回 None 。反之,它应该返回一个二元组 self 和 other ,这两者均已被转换成相同的类型。

类的表示

  • __str__(self)

    定义对类的实例调用 str() 时的行为。

  • __repr__(self)

    定义对类的实例调用 repr() 时的行为。str()repr() 最主要的差别在于“目标用户”。 repr() 的作用是产生机器可读的输出(大部分情况下,其输出可以作为有效的Python代码),而 str() 则产生人类可读的输出。

  • __unicode__(self)

    定义对类的实例调用 unicode() 时的行为。 unicode()str() 很像,只是它返回unicode字符串。注意,如果调用者试图调用 str() 而你的类只实现了 __unicode__() ,那么类将不能正常工作。所有你应该总是定义 __str__() ,以防有些人没有闲情雅致来使用unicode。

  • __format__(self)

    定义当类的实例用于新式字符串格式化时的行为,例如, "Hello, 0:abc!".format(a)会导致调用 a.__format__("abc") 。当定义你自己的数值类型或字符串类型时,你可能想提供某些特殊的格式化选项,这种情况下这个方法会非常有用。

  • __hash__(self)

    定义对类的实例调用 hash() 时的行为。它必须返回一个整数,其结果会被用于字典中键的快速比较。同时注意一点,实现这个方法通常也需要实现 __eq__ ,并且遵守如下的规则: a == b 意味着 hash(a) == hash(b)

  • __nonzero__(self)

    定义对类的实例调用 bool() 时的行为,根据你自己对类的设计,针对不同的实例,这个方法应该相应地返回True或False。

  • __dir__(self)

    定义对类的实例调用 dir() 时的行为,这个方法应该向调用者返回一个属性列表。一般来说,没必要自己实现 __dir__

访问控制

  • __getattr__(self, name)

    当用户试图访问一个根本不存在(或者暂时不存在)的属性时,你可以通过这个魔法方法来定义类的行为。这个可以用于捕捉错误的拼写并且给出指引,使用废弃属性时给出警告(如果你愿意,仍然可以计算并且返回该属性),以及灵活地处理AttributeError。只有当试图访问不存在的属性时它才会被调用,所以这不能算是一个真正的封装的办法。

  • __setattr__(self, name, value)

    __getattr__ 不同, __setattr__ 可以用于真正意义上的封装。它允许你自定义某个属性的赋值行为,不管这个属性存在与否,也就是说你可以对任意属性的任何变化都定义自己的规则。然后,一定要小心使用 __setattr__ ,这个列表最后的例子中会有所展示。

  • __delattr__(self, name)

    这个魔法方法和 __setattr__ 几乎相同,只不过它是用于处理删除属性时的行为。和 __setattr__ 一样,使用它时也需要多加小心,防止产生无限递归(在 __delattr__ 的实现中调用 del self.name 会导致无限递归)。

  • __getattribute__(self, name)

    __getattribute__ 看起来和上面那些方法很合得来,但是最好不要使用它。 __getattribute__ 只能用于新式类。在最新版的Python中所有的类都是新式类,在老版Python中你可以通过继承 object 来创建新式类。 __getattribute__ 允许你自定义属性被访问时的行为,它也同样可能遇到无限递归问题(通过调用基类的 __getattribute__ 来避免)。 __getattribute__ 基本上可以替代 __getattr__ 。只有当它被实现,并且显式地被调用,或者产生 AttributeError 时它才被使用。 这个魔法方法可以被使用(毕竟,选择权在你自己),我不推荐你使用它,因为它的使用范围相对有限(通常我们想要在赋值时进行特殊操作,而不是取值时),而且实现这个方法很容易出现Bug。

自定义序列

有许多办法可以让你的Python类表现得像是内建序列类型(字典,元组,列表,字符串等)。

  • __len__(self)

    返回容器的长度,可变和不可变类型都需要实现。

  • __getitem__(self, key)

    定义对容器中某一项使用 self[key] 的方式进行读取操作时的行为。这也是可变和不可变容器类型都需要实现的一个方法。它应该在键的类型错误式产生 TypeError 异常,同时在没有与键值相匹配的内容时产生 KeyError 异常。

  • __setitem__(self, key)

    定义对容器中某一项使用 self[key] 的方式进行赋值操作时的行为。它是可变容器类型必须实现的一个方法,同样应该在合适的时候产生 KeyErrorTypeError 异常。 __iter__(self, key) 它应该返回当前容器的一个迭代器。迭代器以一连串内容的形式返回,最常见的是使用 iter() 函数调用,以及在类似 for x in container:的循环中被调用。迭代器是他们自己的对象,需要定义 __iter__ 方法并在其中返回自己。

  • __reversed__(self)

    定义了对容器使用 reversed() 内建函数时的行为。它应该返回一个反转之后的序列。当你的序列类是有序时,类似列表和元组,再实现这个方法。

  • __contains__(self, item)

    __contains__ 定义了使用 innot in 进行成员测试时类的行为。你可能好奇为什么这个方法不是序列协议的一部分,原因是,如果__contains__ 没有定义,Python就会迭代整个序列,如果找到了需要的一项就返回 True 。

  • __missing__(self ,key)

    __missing__ 在字典的子类中使用,它定义了当试图访问一个字典中不存在的键时的行为(目前为止是指字典的实例,例如我有一个字典 d , "george" 不是字典中的一个键,当试图访问 d["george"] 时就会调用 d.__missing__("george") )。

反射

  • __instancecheck__(self, instance)

    检查一个实例是否是你定义的类的一个实例(例如 isinstance(instance, class) )。

  • __subclasscheck__(self, subclass)

    检查一个类是否是你定义的类的子类(例如 issubclass(subclass, class) )。

可调用对象

  • __call__(self, [args...])

    允许类的一个实例像函数那样被调用。本质上这代表了 x()x.__call__() 是相同的。注意 __call__ 可以有多个参数,这代表你可以像定义其他任何函数一样,定义 __call__ ,喜欢用多少参数就用多少。

上下文管理器

  • __enter__(self)

    定义使用 with 声明创建的语句块最开始上下文管理器应该做些什么。注意 __enter__ 的返回值会赋给 with 声明的目标,也就是 as 之后的东西。

  • __exit__(self, exception_type, exception_value, traceback)

    定义当 with 声明语句块执行完毕(或终止)时上下文管理器的行为。它可以用来处理异常,进行清理,或者做其他应该在语句块结束之后立刻执行的工作。如果语句块顺利执行, exception_type , exception_valuetraceback 会是 None 。否则,你可以选择处理这个异常或者让用户来处理。如果你想处理异常,确保 __exit__ 在完成工作之后返回 True 。如果你不想处理异常,那就让它发生吧。

创建描述符对象

  • __get__(self, instance, owner)

    定义当试图取出描述符的值时的行为。 instance 是拥有者类的实例, owner 是拥有者类本身。

  • __set__(self, instance, owner)

    定义当描述符的值改变时的行为。 instance 是拥有者类的实例, value 是要赋给描述符的值。

  • __delete__(self, instance, owner)

    定义当描述符的值被删除时的行为。instance 是拥有者类的实例。

拷贝

  • __copy__(self)

    定义对类的实例使用 copy.copy() 时的行为。 copy.copy() 返回一个对象的浅拷贝,这意味着拷贝出的实例是全新的,然而里面的数据全都是引用的。也就是说,对象本身是拷贝的,但是它的数据还是引用的(所以浅拷贝中的数据更改会影响原对象)。

  • __deepcopy__(self, memodict=)

    定义对类的实例使用 copy.deepcopy() 时的行为。 copy.deepcopy() 返回一个对象的深拷贝,这个对象和它的数据全都被拷贝了一份。 memodict 是一个先前拷贝对象的缓存,它优化了拷贝过程,而且可以防止拷贝递归数据结构时产生无限递归。当你想深拷贝一个单独的属性时,在那个属性上调用 copy.deepcopy(),使用 memodict作为第一个参数。