B12_可迭代对象|迭代器|生成器详解

可迭代对象

1. 什么是可迭代对象

  1. 可迭代对象,只要对象的内部实现了__iter__()方法,这个对象就是可迭代对象
  2. 可迭代可以调用iter(obj),获取一个迭代器
  3. 可以通过isinstance(obj,collections.abc.Iterable)来判断是否是可迭代对象
  4. 如果么有实现__iter__方法,但是实现了__getitem__方法,这个对象也是可迭代对象.
    但是它的类型不是Iterable类型,只是可以迭代
  5. 可迭代对象可以通过 for elem in iterable的方式进行遍历
  6. 内置函数iter(iterable) 可以获得迭代器对象Iterator,然后通过next(Iterator),可以获取访问下一个元素
  • 常见的可迭代对象

  • 可迭代对象的本质

    1. 当要迭代一个对象的时候,系统会调用iter(obj)方法
    2. 内置的iter(obj)方法会做以下的事情
    3. 首先是检查对象是否实现了__iter__方法,如果实现了__iter__方法,调用它获得一个迭代器
    4. 如果没有实现__iter__方法,但是实现了__getitem__方法,python解释器会创建一个迭代器,尝试按照顺序(从索引0开始)获取元素
    5. 如果尝试失败,python会抛出TypeError异常
  • 自定义的可迭代对象

    如果没有实现__iter__()方法,但是实现了__getitem__方法,这个对象也是可以迭代的,只是它的类型和Iterable不是同类型的,但是可以使用for循环进行迭代

2. 什么是迭代器

  1. 迭代器是一个保存了位置状态的对象,从第一个元素开始访问,直到所有的元素被访问完结束
  2. 迭代器只能往前不能往后
  3. 迭代器必须是实现了__iter__方法和__next__方法
  4. __iter__方法返回一个带有___next__方法的对象,也就是迭代器本身,调用iter(obj)的时候会被隐式调用,当然你也可以显示调用,一般不建议显式调用这种内置的魔法方法.
  5. __next__方法将逐一的访问容器中的元素.当访问到最后元素的下一个元素的时候,引发StopIteration异常,调用next()的时候,会隐式的调用__next__方法.
  6. 迭代器可以通过内置函数iter(iterable)获取
  7. 判断一个对象是否是迭代器可以通过isinstance(obj,collections.abc.Iterator)的方式
  8. __iter__方法返回迭代器本身(self),__next__方法返回单个元素

  • 自定义一个迭代器,模拟range()函数

3. 生成器

  1. 生成器是一种特殊的迭代器,它不需要实现__iter____next__方法
  2. 实现方式有两种:生成器函数(带yield的函数)生成器表达式
  3. 生成器可以传入数据(通过send),迭代器不行
  4. 生成器不会一次把所有的元素都加载到内存,而是在调用的时候才生成返回结果
  5. 可以通过for循环进行迭代(因为它也是迭代器)
  6. 生成器和函数的区别是,生成器有yield关键字,每次调用的时候都返回yield后面的表达式的值,
    并且会记住这个生成器函数的执行位置,下次迭代的时候,从yield的下一条语句开始执行
  7. 通过next(gen)的方式可以获取生成器的下一条yield的值,for循环执行的时候也是一样的,在遇到
    StopIteration异常的时候结束
  8. .sendnext()一样,都能让生成器前进一步(遇到下一个yield后者没有报异常),但是send()能传入一个参数,这个参数是上一次yield表达式的结果.send()改变的是上一次yield的表达式的结果,所以生成器第一次调用的时候,如果使用了send,只能使用.send(None),因为是第一次调用,还没有yield表达式的结果给send后面的参数赋值接收 .send(None)和调用一次next()的结果和过程是一致的
  • 生成器函数(带yield关键字的函数)
    在这里插入图片描述

  • 带send()的生成器函数
    在这里插入图片描述

  • 生成器表达式

    1. 列表推导式的[]改成()就是生成器表达式
    2. 语法结果就是(res for element in iterable if expression)
    3. 生成器表达式的结果是一个生成器对象,可以迭代和使用next()进行访问

4. 容器|可迭代对象|迭代器|生成器之间的关系

Guess you like

Origin blog.csdn.net/Fioman_GYM/article/details/120626539