生成器
如果一个列表可以通过不停地计算得到它的元素值,那么就不需要直接进行创建,而是一边循环一边计算。这种机制,就叫生成器,即generator。
- ()生成方式
List = [x * x for x in range(5)]
print(List)
输入:
generator = (x * x for x in range(5))
generator
输出:
<generator object <genexpr> at 0x00000163D98C5DB0>
我们创建的List是列表,而generator就是生成器。生成器有两种使用方案,一种是next()函数,一种是for循环。
#第一种,不断使用next()访问
generator = (x * x for x in range(5))
next(generator)
#for循环访问.此方法比较推荐。
for k in generator:
print(k)
- yield方法定义生成器
如果一个函数中带yield语句,那么这个函数就是生成器。函数被调用的时候,可以使用next()或者for循环对函数进行调用,每次调用的时候,都会在yield处暂停,等待下一次循环。实例如下:
def geneByYield(n):
i = 0
while i < n:
yield i
i += 1
return "done"
gene = geneByYield(3)
print(gene)
for k in gene:
print(k)
输出:
<generator object geneByYield at 0x00000163D99A39E8>
0
1
2
如果,在使用next函数调用生成器的时候,遍历结束会抛出StopIteration异常,代表遍历结束,所以,使用next方法遍历时候,捕获这个异常代表结束即可。
迭代器
python中使用for循环的结构有两种,一种是集合数据类型,也就是List,Tuple,Dict等,另一种是上文介绍的生成器。
首先,关于python中的Iterable和Iterator。我们知道集合数据类型可以使用for循环,但是不可使用next访问,因为集合数据类型属于Iterable,却不是Iterator。例如:
输入:
list = [1,2,3]
for k in list:
print(k)
next(list)
输出:
1
2
3
---------------------------------------------------------------------------
TypeError Traceback (most recent call last)
<ipython-input-41-11bf18815824> in <module>()
3 print(k)
4
----> 5 next(list)
TypeError: 'list' object is not an iterator
如果需要使用next访问,也就是得到集合元素的迭代器,那么可以使用iter函数。
输入:
list = [1,2,3]
iterL = iter(list)
while True:
try:
k = next(iterL)
print("Done")
输出:
1
2
3
Done
自建迭代器
在开发过程中,我们可能需要创建的类需要迭代功能。那么,我们需要实现两个方法: _ _ iter_ _() 与 _ _ next _ _()。这样,我们就可以将此类实例传入iter方法,生成迭代器。
class MyIter:
def __iter__(self):#生成生成器时候调用
self.value = 1
return self
def __next__(self):#next方法调用的时候调用
self.value += 1
return self.value
myIter = MyIter()
myIterInstance = iter(myIter)
while True:
k = next(myIterInstance)
if k >= 3:
print("Done")
break
else:
print(k)
输出:
2
Done