Day 11 迭代器、生成器
迭代器
可迭代对象:str list dict,tuple,set,range()
可迭代对象满足可迭代协议,即内部含有__iter__()方法
判断可迭代对象?
1.查看__iter__()方法在不在对象内
dic = {'name':'alex'}
print('__iter__' in dir(s1))
print('__iter__' in dir(dic))
2.函数法
from collections import Iterable
from collections import Iterator
print(isinstance('alex',Iterable)) # True
print(isinstance('alex',Iterator)) # True
返回True即为可迭代对象
迭代器:
对象内部含有__iter__方法且含有__next__方法就是迭代器.
可迭代对象vs迭代器
1, 可迭代对象不能取值,迭代器是可以取值的。
2, 迭代器非常节省内存。
3,迭代器每次只会取一个值。(__next__方法取值。)
4,,迭代器单向的,一条路走到头
lis = [1, 2, 3] # 可迭代对象 ite1 = lis.__iter__() #迭代器 print(ite1.__next__()) #取值,一次取一个 print(ite1.__next__()) print(ite1.__next__()) print(ite1.__next__())
利用while循环模拟for循环
s1 = 'abcdef'
iter1 = s1.__iter__()
while 1:
try:
print(iter1.__next__())
except StopIteration:
break
生成器
使用yield语句而不是return语句返回结果。yield语句一次返回一个结果,在每个结果中间,挂起函数的状态,以便下次重它离开的地方继续执行
def func1(x):
x += 1
yield x
x += 2
yield x
x += 3
yield x
g1 = func1(5)
print(g1.__next__()) # 一个next对应一个yield
print(g1.__next__())
print(g1.__next__())
print(g1.__next__()) # StopIteration
生成器直接创建,不需要转化,从源头上节省了内存
send
send 与next一样,也是对生成器取值(执行一个yield)
send可以给上一个yield传值
第一个必须是next开头
最后一个yield永远也得不到send传的值
def func1():
count = yield 6
print(count)
count1 = yield 7
print(count1)
yield 8
g = func1()
next(g)
g.send('aaa')
g.send('bbb')
g.send('ccc') StopIteration
列表推导式与生成器表达式
列表推导式
1.循环模式 [变量(加工后的变量) for 变量 in iterable]
l1 = [i for i in range(1,10)] print(l1) l2 = [i**2 for i in range(1,11)] print(l2)
2.筛选模式[变量(加工后的变量) for 变量 in iterable if 条件]
l3 = [i for i in range(1,31) if i % 3 == 0]
print(l3)
g = (i for i in range(101))
print(g.__next__())
print(g.__next__())
print(g.__next__())
print(g.__next__())
for i in range(50):
print(g.__next__())
for i in range(30):
print(g.__next__())
生成器表达式
只需将列表表达式中的[ ]换成()即可。
浙公网安备 33010602011771号