趣味理解迭代器和生成器

学习了这么久Python,那么如果让你说迭代器协议和生成器协议是什么,你是否可以很快速的回答上来。
咳咳咳,好吧,你脑海中有这个概念,但是没办法清楚的做出回答。那让我们重新认识一下他们吧!
迭代器:
1.一辆满载的大客车,这里面坐着一群回家的乘客,在行驶路线的沿途中,没到一个地方,总会有几个人下车,还剩下一小部分在到达终点站的时候就会全部下车。
2.一辆满载的旅游客车,里面坐着去旅行的人,在沿途中,他们并不会下车,等到了旅行地点的时候,乘客便会一个一个从车上全部都下来。
通过上面两个实例,我们便可以引出我们的协议。
1.在大客车的协议就是当你到达目的地的时候,就可以靠边停车,不要求在一个必须在一个地方全都下车。
2.在旅游客车中,旅游公司会和游客指定一个协议,就是不到达目的地,不能下车。
这就是他们两个的协议。
为什么要引出这两个协议呢?
因为我们要引出迭代器,在Python大家在进行循环的时候使用最多的应该就是For循环吧,通常我们会对一个列表、元组、字典、字符串、range函数、文件句柄等进行循环,但是我们却没有办法循环一个整型数字(123)。这是因为它不是一个可迭代的对象,**可迭代协议:在一个对象的方法中必须有 iter() 。**那么怎样知道一个对象中是否有这个方法呢?通过dir([ ])(默认查看全局空间内的属性,也接受一个参数,查看这个参数内的方法或变量)我们可以了解到列表中所有的内置方法,当然我们也可以通过

from collections import Iterable
print(dir([]))
print(isinstance([],Iterable))

我们可以判断这个对象是不是可迭代的对象,是否遵循这个协议。了解到了可迭代协议,我们就可以学习迭代器协议:在对象中有 iter() 和 next() 这两个方法的对象就是迭代器。我们怎样依然可以通过

from collections import Iterator
print(dir([]))
print(isinstance([],Iterator))

来判别列表对象是否为迭代器。到这里把迭代器的协议也算是介绍完了,但是我们的事例的作用是干啥用的,现在我们可以将事例的对比转换为 迭代器 与 for 循环的对比,迭代器相当于事例一,在想要地方下车,就在那下车,有自由。而For循环相当于事例二:不能控制下车的人数,要下就全下,不下则一个不下。
在这个里我们要了解的是,其实for循环就是有迭代器构成,简单用代码解释下

python
a = [1,2,3,4]
num = a.__iter__()
while True:
    a = num.__next__()
    print(a)

大致即使这个流程。下面我们就会想既然for循环是由迭代器构成的,那么为什么我们还需要迭代器,可以回味上面的例子,就可以感觉到它的差别,迭代器可以在你工作写代码的时候,当你想调用一个保存在列表中的某一个值的时候,你首先将它变成迭代器,可以取到想要指定的值,而for循环则没有这么好的定制性,而且迭代器可以很好的减少内存在Python内部的机制就是当你取到一个值的时候,Python才会在内存中去创建空间,这样我们放到for循环中来讲就是,不管这个数据用不用的到你都要创建这个内存,所以内存就会占用很多。这便是我们要引出迭代器。
生成器:
生成器的协议是什么呢?在函数的内部如果有yield的关键字,那么我们就说这个函数是个是个生成器函数,调用这个函数的方法返回的就是,生成器(生成器本本身也是一个迭代器)。
yiled 这个关键字的作用:起到了暂停的作用,它和 return 一样都可以将后面的内容返回给函数的调用。那么为什么要使用生成器,我们可以亲试下面代码作比较

def generator():
    for i in range(2000000000000000000):
        yield 'http://www.baidu.com/image.0.%s'%i

url = generator()
for i in url:
    print(i)
def func():
    for i in range(2000000000000000000):
        print('http://www.baidu.com/image.0.%s'%i)

url2 = func()
print(url2)

在运行的时间大致会相同,但是可以细细聆听电脑的声音。
生成器的优点便会体现出来,在第一个代码中,我们看到两个for循环,他们是同时进行的,每调用里面的数字,就会在内存中创建一个数字,然后返回给生成器,内存里面的数,在消失,所以在生成器节省了大量的内存。在我们处理爬取大量数据的时候使用生成器,可以提高爬虫的稳定性。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值