迭代器和生成器

 list
 dic
 str
 set
 tuple
 f = open()
 range()
 enumerate

以上为可迭代对象
 print(dir([])) #告诉我列表拥有的所有方法
 ret = set(dir([]))&set(dir({}))&set(dir(''))&set(dir(range(10)))

求这些对象拥有的方法

只要是能被for循环的数据类型 就一定拥有__iter__方法
# print([].__iter__())
# 一个列表执行了__iter__()之后的返回值就是一个迭代器

print(set(dir([].__iter__())) - set(dir([])))  #看看迭代器比列表多了什么方法

Iterable 可迭代的 -- > __iter__ #只要含有__iter__方法的都是可迭代的
# [].__iter__() 迭代器 -- > __next__ #通过next就可以从迭代器中一个一个的取值

# 只要含有__iter__方法的都是可迭代的 —— 可迭代协议

迭代器的概念
# 迭代器协议 —— 内部含有__next__和__iter__方法的就是迭代器

# 迭代器协议和可迭代协议
# 可以被for循环的都是可迭代的
# 可迭代的内部都有__iter__方法
# 只要是迭代器 一定可迭代
# 可迭代的.__iter__()方法就可以得到一个迭代器
# 迭代器中的__next__()方法可以一个一个的获取值

# for循环其实就是在使用迭代器

for循环列表时执行时实际调用[].__iter__方法,生成一个新的迭代器,新的迭代器从头开始迭代

迭代器的好处:
# 从容器类型中一个一个的取值,会把所有的值都取到。
# 节省内存空间
#迭代器并不会在内存中再占用一大块内存,
# 而是随着循环 每次生成一个
# 每次next每次给我一个

生成器就是迭代器


#只要含有yield关键字的函数都是生成器函数
# yield不能和return共用且需要写在函数内

 def generator():
     print(1)
     yield 'a'
     print(2)
     yield 'b'
     yield 'c'
g = generator()

对生成器函数赋值时会生成一个新的生产器

调用一次g.__next__()会返回一个yield的值,

下次调用返回下个yield的值

b = generator()#又生成一个新的生成器调用一次b.__next__()会返回第一个yield的值,而不是继续g生产器的yield的值
所以for循环列表的时候都是从第一个yield执行
for循环g或b时看之前是否调用过生产器,再接着执行。


def wahaha():
    for i in range(2000000):
        yield '娃哈哈%s'%i
# g = wahaha()
# g1 = wahaha()
# print(g.__next__())
# print(g1.__next__())

# g = wahaha()
# count = 0
# for i in g:
#     count +=1
#     print(i)
#     if count > 50:
#         break
# # print('*******',g.__next__())
# for i in g:
#     count +=1
#     print(i)
#     if count > 100:
#         break

 



posted @ 2018-11-29 20:27  曜有丨光  阅读(107)  评论(0编辑  收藏  举报