一,可迭代的&可迭代对象
1.一个一个的取值就是可迭代的 iterable
#str list tuple set dict
#可迭代的 ——对应的标志 __iter__
2.判断一个变量是不是一个可迭代的
# print('__iter__' in dir(list))
# print('__iter__' in dir([1,2,3]))
3.可迭代协议——凡是可迭代的内部都有一个__iter__方法
二,迭代器
1.将可迭代的转化成迭代器
1 #!/usr/bin/env python 2 #_*_coding:utf-8_*_ 3 4 # iterator #迭代器 5 # iterator iterable#可迭代对象 6 l = [1,2,3,4,5] 7 for i in l: 8 print(i) 9 print(iter(l)) #内置函数 iter == l._iter_() 10 l.__iter__() 11 l_iterator = iter(l) 12 print(set(dir(l_iterator))-set(dir(l))) 13 print(next(l_iterator)) #迭代器就要通过next方法取值
2.迭代器小结
#迭代器里既有iter方法,又有next方法 ——迭代器协议
#通过iter(o)得到的结果就是一个迭代器,
#o是一个可迭代的
#迭代器 大部分都是在python的内部去使用的,我们直接拿来用就行了
#迭代器:内置__iter__和__next__方法
1 #!/usr/bin/env python 2 #_*_coding:utf-8_*_ 3 4 l = [1,2,3,4,5] 5 l_iterator = iter(l) 6 print(l_iterator.__next__()) 7 print(l_iterator.__next__()) 8 print(l_iterator.__next__()) 9 print(l_iterator.__next__()) 10 print(l_iterator.__next__()) 11 next(l_iterator) #==l_iterator.__next__() 12 # while True: 自己写相当于for循环 13 # try: 14 # print(next(l_iterator)) 15 # except StopIteration: 16 # break
3.判断是否是迭代器 和 可迭代对象的简便方法
1 #!/usr/bin/env python 2 #_*_coding:utf-8_*_ 3 4 from collections import Iterable 5 from collections import Iterator 6 # s = 'abc' 7 # print(isinstance(s,Iterable)) s 是不是一个可迭代对象 8 # print(isinstance(s,Iterator)) s 是不是一个迭代对象 9 # print(isinstance(iter(s),Iterator))
4.可迭代的和迭代器
#不管是一个迭代器还是一个可迭代对象,都可以使用for循环遍历
#迭代器出现的原因 帮你节省内存
三,生成器
#生成器函数
#生成器的本质就是迭代器
1 #!/usr/bin/env python 2 #_*_coding:utf-8_*_ 3 4 def func(): 5 print('aaaa') 6 a = 1 7 yield a #返回第一个值 8 print('bbbb') 9 yield 12 #返回第二个值 10 #错误取值,相当于三个新的生成器 14 # print(next(func() )) #取第一个值 15 # print(next(func() )) #取第一个值 16 # print(next(func() )) #取第一个值 17 #正确取值,都是同一个生成器 18 # ret = func() #拿到一个生成器 19 # # print(ret) 20 # print(next(ret)) #取第一个值 21 # print(next(ret)) #取第二个值 22 # print(next(ret)) #取第三个值 会报错 因为没有第三个值
3,1 生成器做衣服实例
1 #/usr/bin/env python 2 #_*_coding:utf-8_*_ 3 4 def make_cloth(): 5 for i in range(2000000): 6 yield "第%s件衣服"%i 7 # szq = make_cloth() 8 # print(next(szq)) 9 # print(next(szq)) 10 # 11 # print(next(szq)) 12 # for i in range(50): 13 # print(next(szq))
3.2 监听文件实例
1 #!/usr/bin/env python 2 #_*_codingLutf-8_*_ 3 4 #监听文件 tail -f 5 import time 6 def tail(filename): 7 with open(filename) as f: 8 f.seek(0, 2) #从文件末尾算起 9 while True: 10 line = f.readline() # 读取文件中新的文本行 11 if not line: 12 time.sleep(0.1) 13 continue 14 yield line 15 16 # for line in tail('tmp_file'): 17 # print(line,end = '')
3.3 计算移动平均值
1 #!/usr/bin/env python 2 #_*_coding:utf-8_*_ 3 4 #7日平均年化收益 5 def averager(): 6 total = 0 7 day = 0 8 avrage = 0 9 while True: 10 day_num = yield avrage #return avrage 11 total += day_num 12 day += 1 13 avrage = total/day 14 15 # avg = averager() 16 # num = next(avg) #激活生成器 avg.send(),什么都不send和next效果一样 17 # print(avg.send(10)) #传值 next 18 # print(avg.send(20))
3.4 带装饰器的生成器
1 #!/usr/bin/env python 2 #_*_codingLutf-8_*_ 3 4 def wrap(func): 5 def inner(*args,**kwargs): 6 g = func(*args,**kwargs) 7 next(g) 8 return g 9 return inner 10 11 @wrap 12 def averager(): 13 total = 0 14 day = 0 15 avrage = 0 16 while True: 17 day_num = yield avrage #return avrage 18 total += day_num 19 day += 1 20 avrage = total/day 21 22 # g = averager() 23 # print(g.send(10)) 24 # print(g.send(20))