一、容器

容器是一种把多个元素组织在一起的数据结构,容器中的元素可以逐个地迭代获取,可以用in, not in关键字判断元素是否包含在容器中。通常这类数据结构把所有的元素存储在内存中。

 >>> 4 in [3, 4]
True
>>> 4 in (3, 4)
True

二、可迭代对象Iterable和迭代器Iterator

我们在用for ... in ...语句循环时,in后面跟随的对象要求是可迭代对象,即可以直接作用于for循环的对象统称为可迭代对象(Iterable),如list、tuple、dict、set、str等。

可迭代对象是实现了__iter__()方法的对象,而迭代器(Iterator)则是实现了__iter__()和__next__()方法的对象,可以显示地获取下一个元素。这种可以被next调用并不断返回下一个值的对象称为迭代器。迭代器一定是可迭代对象,反过来则不一定成立。

__iter__返回迭代器自身,__next__返回容器中的下一个值。

iter()函数可以把一个可迭代对象转换成一个迭代器。

用iter()函数可以把list、dict、str等Iterable变成Iterator,例如:

 i = iter([1, 2, 3])
print(i.__next__())
print(i.__next__())
print(i.__next__())
print(i.__next__())
1
2
3
Traceback (most recent call last):
File "4.py", line 12, in <module>
print(i.__next__())
StopIteration

判断一个对象是否是可迭代对象的方法:

1 >>> from collections import Iterable
2 >>> isinstance([1, 2, 3], Iterable)
3 True
4 >>> isinstance((1, 2, 3), Iterable)
5 True
6 >>> isinstance({'one': 1}, Iterable)
7 True
8 >>> isinstance('abc', Iterable)
9 True
10 >>> isinstance(b'abc', Iterable)
11 True
12 >>> isinstance(bytearray('abc', encoding='utf-8'), Iterable)
13 True

判断一个对象是否是迭代器:

 1 >>> from collections import Iterator
2 >>> isinstance((x for x in range(10)), Iterator)
3 True
4 >>> isinstance([], Iterator)
5 False
6 >>> isinstance({}, Iterator)
7 False
8 >>> isinstance(b'abc', Iterator)
9 False

for..in..循环的运行实质:

更直观地感受迭代器内部的执行过程,我们自定义一个迭代器,以斐波那契数列为例:

 class Fib:
def __init__(self):
self.prev = 0
self.curr = 1 def __iter__(self):
return self def __next__(self):
value = self.curr
self.curr += self.prev
self.prev = value
return value >>> f = Fib()
>>> list(islice(f, 0, 10))
[1, 1, 2, 3, 5, 8, 13, 21, 34, 55]

三、生成器

生成器(generator)就是一个能返回迭代器的函数,其实就是定义一个迭代算法,可以理解为一个特殊的迭代器。调用这个函数就得到一个迭代器,生成器中的yield相当于一个断点,执行到此返回一个值后暂停,从而实现next取值。

生成器算得上是Python语言中最吸引人的特性之一,生成器其实是一种特殊的迭代器,不过这种迭代器更加优雅。它不需要再像上面的类一样写__iter__()和__next__()方法了,只需要一个yiled关键字。 生成器一定是迭代器(反之不成立),因此任何生成器也是以一种懒加载的模式生成值。用生成器来实现斐波那契数列的例子是:

 def fib():
prev, curr = 0, 1
while True:
yield curr
prev, curr = curr, curr + prev >>> f = fib()
>>> list(islice(f, 0, 10))
[1, 1, 2, 3, 5, 8, 13, 21, 34, 55]

fib就是一个普通的python函数,它特殊的地方在于函数体中没有return关键字,函数的返回值是一个生成器对象。当执行f=fib()返回的是一个生成器对象,此时函数体中的代码并不会执行,只有显示或隐示地调用next的时候才会真正执行里面的代码。

生成器在Python中是一个非常强大的编程结构,可以用更少地中间变量写流式代码,此外,相比其它容器对象它更能节省内存和CPU,当然它可以用更少的代码来实现相似的功能。

 def something():
result = []
for ... in ...:
result.append(x)
return result

都可以用生成器函数来替换:

def something():
result = []
for ... in ...:
result.append(x)
return result

现在就可以动手重构你的代码了,但凡看到类似:

 def iter_something():
for ... in ...:
yield x

四、生成表达式

生成器表达式(generator expression)是列表推倒式的生成器版本,看起来像列表推导式,但是它返回的是一个生成器对象而不是列表对象。

 >>> a = (x*x for x in range(10))
>>> a
<generator object <genexpr> at 0x401f08>
>>> sum(a)
285

python 容器 生成器 迭代器 总结的更多相关文章

  1. python初识生成器 迭代器

    生成器 带有 yield 的函数在 Python 中被称之为 generator(生成器) def xragns(): #定义函数生成器 print('小伙') yield ('好') #加上yiel ...

  2. Python中生成器,迭代器,以及一些常用的内置函数.

    知识点总结 生成器 生成器的本质就是迭代器. 迭代器:Python中提供的已经写好的工具或者通过数据转化得来的. 生成器:需要我们自己用Python代码构建的 创建生成器的三种方法: 通过生成器函数 ...

  3. python基础 生成器 迭代器

    列表生成式: a=[1,2,3] print a b=[i*2 for i in range(10)] #i循环10次,每一个i的值乘2就是列表中的值.列表生成式 print b >>[1 ...

  4. 第四天python3 python解析式-生成器-迭代器

    标准库datetime datetime模块  对日期.时间.时间戳的处理 datetime类 类方法: today() 返回本地时区当前时间的datetime对象: now(tz=None) 返回当 ...

  5. python高级之生成器&迭代器

    python高级之生成器&迭代器 本机内容 概念梳理 容器 可迭代对象 迭代器 for循环内部实现 生成器 1.概念梳理 容器(container):多个元素组织在一起的数据结构 可迭代对象( ...

  6. 第三篇:python高级之生成器&迭代器

    python高级之生成器&迭代器   python高级之生成器&迭代器 本机内容 概念梳理 容器 可迭代对象 迭代器 for循环内部实现 生成器 1.概念梳理 容器(container ...

  7. python学习 day13 迭代器,生成器,枚举对象

    一.复习 1.闭包:定义在函数内部的函数(被函数嵌套的函数) 2.装饰器:闭包的一个应用场景 -- 为一个函数添加新功能的工具 3.开放封闭原则:不能修改源代码,不能修改调用方式,但可以对外提供增加新 ...

  8. Python中生成器和迭代器的区别(代码在Python3.5下测试):

    https://blog.csdn.net/u014745194/article/details/70176117 Python中生成器和迭代器的区别(代码在Python3.5下测试):Num01–& ...

  9. python 生成器 迭代器

    阅读目录 一 递归和迭代 二 什么是迭代器协议 三 python中强大的for循环机制 四 为何要有for循环 五 生成器初探 六 生成器函数 七 生成器表达式和列表解析 八 生成器总结 一 递归和迭 ...

随机推荐

  1. C语言知识结构之二

    C语言的知识结构整理成思维导图,例如以下图所看到的: 这张图的总体思路是: 用C敲代码.该学会什么? 要用C写的更好,改学会什么? 事实上.仅仅要是分层的知识结构,大致的思路是: 首先,研究本层的知识 ...

  2. 关于结构体的具体解说,C、C++中的差别

    1. C.C++内置的类型分两种,一种是基本数据类型.一种是复合数据类型.此处我们要讲的结构体便是复合数据类型. 先来讨论一下结构体存在的意义吧.或许你觉得主要的数据类型就够了,为什么还要有结构题这样 ...

  3. linux系统之shell编程-正則表達式

    shell编程正則表達式: 1:元字符   [ ]  .   *  ? + ( )  |  {  }  ^  $ 2 : [a-z0-9]  表示匹配随意数字和字母的一个 3 :  [^a-z]    ...

  4. 手机号码归属地查询免费api接口代码

    依据手机号码查询用户的卡类型.运营商.归属地.区域等信息. 手机归属地实体类 package org.wx.xhelper.model; /** * 手机归属地 * @author wangxw * ...

  5. HDU 2955 Robberies(01背包变形)

    Robberies Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total S ...

  6. 民大OJ 1668 追杀系列第二发

    追杀系列第二发 时间限制(普通/Java) : 1000 MS/ 3000 MS          运行内存限制 : 65536 KByte 总提交 : 57            测试通过 : 16 ...

  7. android-custom-tab-with-viewpager

    https://github.com/eltld/android-custom-tab-with-viewpager

  8. Go语言测试代码

    第一次学go语言,测试代码 package main import "fmt" var age int; const sex = 0 func init() { fmt.Print ...

  9. scrollTo(String text) and scrollToExact(String text) method of Android Driver not working

    Using the scrollTo(String text) and scrollToExact(String text) method of Android Driver. However the ...

  10. Testng 运行报错:"Total tests run: 0, Failures: 0, Skips: 0"以及找不到class文件的问题

    "Total tests run: 0, Failures: 0, Skips: 0" This means that there were no tests executed a ...