以下都是我自学Python整理的笔记,以便帮助学习。
许多容器都是可迭代对象,但也有很多不是容器的对象也是可迭代对象,比如处于打开状态的files,socket等。
2.可迭代对象都具有__iter__函数,并且可迭代对象通过iter()函数会返回一个迭代器,迭代器内部具有一个状态,该状态用于记录当前迭代所在的位置方便下一次迭代。
3.迭代器有一种具体的迭代器类型,比如list_iterator,set_iterator。可迭代对象实现了__iter__方法,该方法返回一个迭代器对象。
迭代器(iterator)
1.迭代器是一种带状态的对象,它能在你调用next()方法的时候返回容器中的下一个值,任何实现了__iter__和__next__方法的对象都是迭代器,__iter__返回迭代器本身,__next__返回容器中的下一个值,当遍历到最后一个值,没有元素的时候会抛出StopIteration异常。
2. itertools函数返回的都是迭代器对象。
3.迭代器不会一次性把所有元素加载到内存,而是需要的时候才生成返回结果。迭代器就像一个懒加载的工厂,等到有人需要的时候才给它生成值返回,没调用的时候就处于休眠状态等待下一次调用。
4.三种常见的迭代器:
这个可以理解成一条无限延长的直线。
itertools模块下的count(start)函数,star为起点。
help(itertools.count)#查看帮助文档
count(start=0, step=1) --> count object | Return a count object whose .__next__() method returns consecutive values. def count(firstval=0, step=1): | x = firstval | while 1: | yield x | x += step
例子:
import itertools >>> counter = itertools.count(start=2) >>> next(counter) 2 >>> next(counter) 3 >>> next(counter) 4
(2)通过一个有限序列生成无限迭代器,这个可以理解为是一个圆,无限遍历。
itertools下的cycle(iterable)函数,参数是一个可迭代对象。
help(itertools.cycle) cycle(iterable) --> cycle object | Return elements from the iterable until it is exhausted. | Then repeat the sequence indefinitely. #从可迭代对象取出所有的元素然后无限循环
例子:
>>> from itertools import cycle >>> colors = cycle(['red','white','blue']) >>> next(colors) 'red' >>> next(colors) 'white' >>> next(colors) 'blue' >>> next(colors) 'red' >>> next(colors) 'white'
(3)有限迭代器,其实就是无限迭代器中截取一段序列。
itertools下的islice(iterable, start, stop[, step])
iterable为可迭代对象,start为起点,不给start值时,默认从0开始,给值时会默认从起点的下一个元素开始遍历,stop为终点,step为步长。
help(itertools.islice)
class islice(builtins.object) | islice(iterable, stop) --> islice object | islice(iterable, start, stop[, step]) --> islice object #返回一个迭代器,iterable可迭代对象,start如果不设置为0,设置了会默认从start下一个元素开始遍历,stop终止,step步长。
例子:
>>> from itertools import islice >>> num = cycle((1,2,3)) >>> limited = islice(num,0,4) >>> next(limited) 1 >>> next(limited) 2 >>> next(limited) 3 >>> next(limited) 1 >>> next(limited) Traceback (most recent call last): File "<stdin>", line 1, in <module> StopIteration
2.生成器有延迟作用,就是有需要的时候才会生产数据,不是立即产生结果。
生成器只能遍历一次。
4.两种方法得到生成器:
(1)定义生成器函数,返回值用yield而不是return,yield和return最本质的区别在于return会终止函数,不会保留函数中的变量,再次如果再次调用函数时从头开始;而yield相当于在是冻结函数,给了函数一个状态,让他暂时挂起保留此次调用的变量,下一次继续这个位置调用。
看例子:
#用return
def func(var): while var > 0: print(var) return var var -= 1 d = func(10) print(type(d)) 10 <class 'int'>
#用yield def func(var): while var > 0: yield var #return var var -= 1 d = func(10) print(type(d)) <class 'generator'>#type看到d是一个生成器
#所以我们可以对d进行for循环遍历
for i in d:
print(i)
10 9 8 7 6 5 4 3 2 1
(2)生成器表达式:把列表推导式的[ ]改成( )
使用生成器表达式取代列表推导式可以同时节省 cpu 和 内存(RAM)。
gen = (i for i in range(10))
gen = (i for i in range(10)) print(type(gen)) for var in gen: print(var) <class 'generator'> 0 1 2 3 4 5 6 7 8 9