迭代器
1.迭代器协议
对象必须提供一个 next 方法,执行该方法要么返回迭代中的下一项,要么就引起一个Stoplteration异常,以终止迭代(只能往后走不能往前退)
2.可迭代对象
实现了迭代器协议的对象(如何实现:对象内部定义一个_iter_()方法)
协议是一种约定,可迭代对象实现了迭代器协议,python的内部工具(如 for循环,sum,min,max函数等)使用迭代器协议访问对象
3.关于for循环机制
for循环的本质:循环所有对象,全都是使用迭代器协议
思考:for 循环的本质是遵循迭代器协议去访问对象,那么for循环的对象肯定都是迭代器。那么既然这样,for循环可以遍历(字符串、列表、元祖、字典、集合、
文件对象),那么这些类型的数据肯定都是可迭代对象。但是我们发现,定义了一个字符串 S = ‘xhg’,却发现S.next()方法,违背了迭代器协议。所以不是
迭代对象。
从不同角度分析问题,得出了不同的结论。要想了解具体怎么回事,需要知道for循环内部做了些什么事情
结论:(字符串、列表、元祖、字典、集合、文件对象)这些都不是可迭代对象,只不过在for循环时,
调用了他们内部的 _iter_() 方法,把他们变成了可迭代对象,然后for循环调用可迭代对象的 _next_()
方法去取值,而且for循环会捕捉Stoplteration异常,以终止迭代
f = [1, 2, 3, 4, 5] for i in f: print(i)
#分析 第一步:iter_f = f.__iter__() #调用了他们内部的 _iter_() 方法,把他们变成了可迭代对象,遵循可迭代协议 第二步:iter_f.__next__() #调用可迭代对象 iter_f 的 __next__() 方法进行取值
#for循环内部等同于做了以下代码的作用: f = [1, 2, 3, 4, 5] iter_f = f.__iter__() print(iter_f) print(iter_f.__next__()) print(iter_f.__next__()) print(iter_f.__next__()) print(iter_f.__next__()) print(iter_f.__next__())
iter_f.__next__() 等同于 next(iter_f)
4.实现列表取值的两种方法
方法一:索引 f = [1, 2, 3, 4, 5] print(f[2])
方法二:利用迭代器思想 iter_f = f.__iter__() print(iter_f.__next__()) print(iter_f.__next__())
5.遍历列表内部全部值的两种方法
方法一:利用 for 循环(基于迭代器协议) f = [1, 2, 3, 4, 5] for i in f: print(i)
方法二:利用 while 循环 f = [1, 2, 3 ,4, 5] index = 0 while index < len(f): print(f[index]) index += 1
思考:并非所有类型的数据遍历都可以用while循环。序列类型字符串、列表、元祖都有下标
使用while循环,利用下标遍历,是可以的。但是对于非序列类型数据,如字典、集合、文件对象
的遍历,while 循环无法实现遍历。但是利用 for 循环可以。
因为for 循环就是基于迭代器协议提供了一个统一的可以遍历所有对象的方法。即在遍历前先调用对象的__iter__()方法,
将对象转换为一个迭代器,然后使用迭代器协议就可以实现循环访问。所以 for 循环较为强大。
举例:
#字典的循环: dic = {'key1':1, 'key2':2} for i in dic: print(i) #执行结果 key1 key2 #for 循环作用: dic = {'key1':1, 'key2':2} iter_dic = dic.__iter__() print(iter_dic.__next__()) print(iter_dic.__next__()) #注意:对于字典,默认遍历的是key值
#文件的循环: f = open('日志文件', 'r+') for i in f: print(i,end='') #执行结果 1111 2222 3333 4444 #注意:for循环每次遍历的是文件的一行内容 #for 循环作用: f = open('日志文件', 'r+') iter_f = f.__iter__() print(iter_f.__next__(), end='') print(iter_f.__next__(), end='') print(iter_f.__next__(), end='') print(iter_f.__next__(), end='')
写在后面:
最近好像有点烦躁
心情也不是很好 阶段性心情差
想打人!!!!
希望睡一觉起来会好一些吧