魔法方法之自定义序列

自定义序列

  自定义序列的相关魔法方法允许我们自己创建的类拥有序列的特性,让其使用起来就像 python 的内置序列(dict,tuple,list,string等)。

  因为如果要定制容器类型的话需要用到这些协议。首先,实现不变容器的话有一个协议:实现不可变容器,你只能定义__len__ 和 __getitem__ (一会会讲更多)。可变容器协议则需要所有不可变容器的所有另外还需要 __setitem__ 和 __delitem__ 。最终,如果你希望你的对象是可迭代的话,你需要定义 __iter__ 会返回一个迭代器。迭代器必须遵循迭代器协议,需要有 __iter__ (返回它本身) 和 next 。 

容器背后的魔法方法

  • __len__(self)

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

  • __getitem__(self, key)

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

  • __setitem__(self, key)

    定义对容器中某一项使用 self[key] 的方式进行赋值操作时的行为。它是可变容器类型必须实现的一个方法,同样应该在合适的时候产生 KeyError 和 TypeError 异常。

  • __iter__(self, key)

    它应该返回当前容器的一个迭代器。迭代器以一连串内容的形式返回,最常见的是使用 iter()函数调用,以及在类似 for x in container: 的循环中被调用。迭代器是他们自己的对象,需要定义 __iter__ 方法并在其中返回自己。

  • __reversed__(self)

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

  • __contains__(self, item)

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

  • __missing__(self ,key)

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

example:

class FunctionalList:
    ‘‘‘一个列表的封装类,实现了一些额外的函数式
    方法,例如head, tail, init, last, drop和take。‘‘‘

    def __init__(self, values=None):
        if values is None:
            self.values = []
        else:
            self.values = values

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

    def __getitem__(self, key):
        # 如果键的类型或值不合法,列表会返回异常
        return self.values[key]

    def __setitem__(self, key, value):
        self.values[key] = value

    def __delitem__(self, key):
        del self.values[key]

    def __iter__(self):
        return iter(self.values)

    def __reversed__(self):
        return reversed(self.values)

    def append(self, value):
        self.values.append(value)

    def head(self):
        # 取得第一个元素
        return self.values[0]

    def tail(self):
        # 取得除第一个元素外的所有元素
        return self.valuse[1:]

    def init(self):
        # 取得除最后一个元素外的所有元素
        return self.values[:-1]

    def last(self):
        # 取得最后一个元素
        return self.values[-1]

    def drop(self, n):
        # 取得除前n个元素外的所有元素
        return self.values[n:]

    def take(self, n):
        # 取得前n个元素
        return self.values[:n]

 参考:http://pycoders-weekly-chinese.readthedocs.io/en/latest/issue6/a-guide-to-pythons-magic-methods.html#id14

时间: 2024-11-07 18:58:09

魔法方法之自定义序列的相关文章

Python3 魔法方法:定制序列

1.基于序列的三大容器 分别是 列表.元组.字符串 2.协议 python中的协议更像是一种指南,例如鸭子类型,一只鸟像鸭子一样走,像鸭子一样叫,像鸭子一样游然后这只鸟就可以叫做鸭子 3.容器类型的协议 如果希望定制的容器是不可变的,那么只需要定义__len__ 和__getitem__ 方法 如果希望定制的容器是可变的,那么还需要定义 __setitem__ 和__delitem__方法 4.魔法方法 _len__(self) 定义当被 len() 调用时的行为(返回容器中元素的个数) __g

Python--29 魔法方法:定制序列

协议是什么? 协议(Protocols)与其他编程语言中的接口很相似,它规定你哪些方法必须要定义.然而,在Python中的协议就是现得不那么正式.事实上,在Python中,协议更像是一种指南. 容器类型的协议 如果希望定制的容器是不可变的话,你只需要定义__len__()和__getitem__()方法. 如果你希望定制的容器是可变的话,除了__len__()和__getitem__()方法,你还需要定义__setitem__()和__delitem__()两个方法. 联系要求 编写一个不可改变

python_面向对象魔法方法指南

原文: http://www.rafekettler.com/magicmethods.html 原作者: Rafe Kettler 翻译: hit9 原版(英文版) Repo: https://github.com/RafeKettler/magicmethods Contents (译)Python魔法方法指南 简介 构造方法 操作符 比较操作符 数值操作符 一元操作符 常见算数操作符 反射算数运算符 增强赋值运算符 类型转换操作符 类的表示 访问控制 自定义序列 预备知识 容器背后的魔法方

python魔法方法-自定义序列

自定义序列的相关魔法方法允许我们自己创建的类拥有序列的特性,让其使用起来就像 python 的内置序列(dict,tuple,list,string等). 如果要实现这个功能,就要遵循 python 的相关的协议.所谓的协议就是一些约定内容.例如,如果要将一个类要实现迭代,就必须实现两个魔法方法:__iter__.next(python3.x中为__new__).__iter__应该返回一个对象,这个对象必须实现 next 方法,通常返回的是 self 本身.而 next 方法必须在每次调用的时

python魔法方法、构造函数、序列与映射、迭代器、生成器

在Python中,所有以__双下划线包起来的方法,都统称为"魔术方法".比如我们接触最多的__init__,魔法方法也就是具有特殊功能的方法. 构造函数 构造函数不同于普通方法,将在对象创建后自动调用它们.也就是在对象创建完成后,自动会调用__init__方法来初始化. 创建一个构造方法 构造方法传参 >>> class FooBar: def __init__(self,value=42): #默认参数 self.somevar = value >>&g

Python基础教程(第九章 魔法方法、属性和迭代器)

本文内容全部出自<Python基础教程>第二版,在此分享自己的学习之路. ______欢迎转载:http://www.cnblogs.com/Marlowes/p/5437223.html______ Created on Marlowes 在Python中,有的名称会在前面和后面都加上两个下划线,这种写法很特别.前面几章中已经出现过一些这样的名称(如__future__),这种拼写表示名字有特殊含义,所以绝不要在自己的程序中使用这样的名字.在Python中,由这些名字组成的集合所包含的方法称

python魔法方法-比较相关

在python2.x的版本中,支持不同类型的比较,其比较原则如下: 内置类型: 1.同一类型: 1.1)数字类型:包含int.float.long.complex.bool(bool类型是int的子类,且True=1, False=0).就按照数字的大小进行比较,例如:   1.2)非数字类型:1.2.1)如果类型中定义了如__cmp__.__gt__等魔法方法,就按照其魔法方法的返回值进行比较,具体如何就是这篇文章接下来要讨论的内容.  1.2.2)如果没有定义上述的魔法方法,就按照 id 函

&lt;&lt;Python基础教程&gt;&gt;学习笔记 | 第09章 | 魔法方法、属性和迭代器

这一章,有点抽象,看着有点蛋疼! 双下划线__future__或单下划线有特殊含义,在Python中,这些名字的集合称为魔法方法:最重要的是__init__和一些处理访问对象的方法,这些方法允许你创建自己的序列或者是映射. ------ 准备工作: 将__metaclass__=type放在模块的最开始位置,以确保类时最新式的.考虑下面两个类 class NewStyle(object): more_code_here class OldStyle: more_code_here 如果文件以__

《Python基础教程》 读书笔记 第九章 魔法方法、属性和迭代器(上)

构造方法 在Python中创建一个构造方法很容易.只要把init方法的名字从简单的init修改为魔法版本__init__即可: >>> class FooBar: ...     def __init__(self): ...         self.somevar=42 ... >>> f=FooBar() >>> f.somevar 42 给构造方法传几个参数 >>> class FooBar: ...     def __in