Python可迭代对象迭代器对象
1.可迭代对象 Iterable
1.1遍历(迭代):依次从对象中把一个个元素取出来的过程
数据类型:str、list、tuple、dict、set等
kediedict_keys dict_values
1.2可迭代对象的条件
1.对象实现了__iter__()方法
2.__iter__()方法返回了迭代器对象
1.3for循环工作原理
1.先通过__iter__()获取可迭代对象的迭代器
2.对获取到的迭代器不断调用__next__()方法来获取下一个值并将其赋值给临时变量i
1.4isinstance():判断一个对象是否是可迭代对象或者是一个一直的数据类型
使用时需要导入模块:from collections import Iterable(Python3.3之前的版本)
from collections.abc import Iterable(3.3之后的版本)
isinstance(o,t) o:对象,t:类型,可以是直接或者间接类名、基本类型或者元组
from collections.abc import Iterable
print(isinstance(123,int)) #True
print(isinstance('1mks',Iterable)) #True
print(isinstance((1,2,3),Iterable)) #True
print(isinstance(143,Iterable)) #False
2.迭代器 Iterable
迭代器是一个可以记住遍历位置的对象,在上一次停留的位置继续去做一些事
通过for循环遍历,就是获取了迭代器,并不断调用__next__()方法
li = [1,2,3,4]
for i in li:
print(i) #1 2 3 4
iter():获取可迭代对象的迭代器
next():一个个去取元素,取完元素后会引发一个异常
2.1迭代器实现的两种方法
第一种方法:
li = [1,2,3,4,5]
#创建一个迭代器对象
li2 = iter(li)
print(li2)
#获取下一条数据
print(next(li2))
print(next(li2))
print(next(li2))
print(next(li2))
print(next(li2))
#取完元素后在使用next()会引发StopIteration异常
print(next(li2))
步骤:
1.iter()调用对象的__iter__(),并把__iter__()方法返回结果作为自己的返回值
2.next()调用对象的__next__(),一个个取出元素
3.所有元素都取完了,__next__()将引发StopIteration异常
第二种方法:
li = [1,2,3,4,5]
#创建一个迭代器对象
li2 = li.__iter__()
print(li2)
#获取下一条数据
print(li2.__next__())
print(li2.__next__())
print(li2.__next__())
print(li2.__next__())
print(li2.__next__())
#取完元素后在使用next()会引发StopIteration异常
print(li2.__next__())
2.2可迭代对象iterable和迭代器对象iterator
凡是可以作用于for循环的都是可迭代对象
凡是可以作用于next()的都是迭代器对象
from collections.abc import Iterable,Iterator
name = 'panda'
print(isinstance(name,Iterator)) #False
print(isinstance(name,Iterable)) #True
name = iter(name) #获取可迭代对象的迭代器
print(isinstance(name,Iterator)) #True
print(isinstance(name,Iterable)) #True
可迭代对象不一定是迭代器对象,迭代器对象一定是可迭代对象
总结:可迭代对象可以通过iter()转化为迭代器对象,如果一个对象拥有__iter__()方法是可迭代对象,如果一个对象有__iter__()和__next__()方法,是迭代器对象
(可以用dir()查看对象中的属性和方法)
2.3迭代器协议
对象必须提供一个next方法,执行该方法要么就返回迭代中的下一项,要么就引发StopIteration异常,来终止迭代
2.4自定义迭代器
两个特性__iter__()和__next__()
class MyIteration(object):
def __init__(self):
self.num = 0
def __iter__(self):
return self #返回的是当前迭代器类的实例对象
def __next__(self):
if self.num == 10:
raise StopIteration("终止迭代,数据已被读取完")
self.num += 1
return self.num
mi = MyIteration() #类中有__iter__()和__next__()方法,创建的对象就是迭代器对象
print(mi)
for i in mi:
print(i) #1 2 3 4 5 6 7 8 9 10
3.生成器 generator
定义:Python中一边循环,一边计算的机制,叫生成器
Python提供的一种非常简便的语法能让我们自己来写出迭代器
使用了yield关键字的函数被称为生成器
3.1生成器表达式
列表推导式格式:[表达式 for 变量 in 列表]
将[]改为()即可
li = [i*5 for i in range(5)]
gen = (i*5 for i in range(5))
print(li) #[0, 5, 10, 15, 20]
print(gen) #<generator object <genexpr> at 0x0000020F7FDC1E48>
print(next(gen)) #0
print(next(gen)) #5
print(next(gen)) #10
print(next(gen)) #15
print(next(gen)) #20
print(next(gen)) #StopIteration
yield的作用:
1.类似return,将指定值或者多个值返回给调用者
2.yield语句一次返回一个结果,在每个结果中间,挂起函数,执行next(),在重新从挂起点继续往下执行(使函数中断,并保存中断状态)
创建生成器
def gen1():
print("开始")
yield 'a' #返回一个’a'并暂停函数,在此处挂起,下一次再从此处恢复运行
yield 'b'
yield 'c'
gen = gen1()
print(gen) #<generator object gen1 at 0x0000019DFBBE1E48>
print(next(gen)) #a
print(next(gen)) #b
print(next(gen)) #c
给列表中追加元素
方法一:循环
def gen2(n):
li = []
for i in range(n):
li.append(i)
print(li)
gen2(4) #[0, 1, 2, 3]
方法二:生成器
def gen2(n):
li = []
a = 0
while a < n:
li.append(a)
yield a
a += 1
print(li) #[0, 1, 2, 3]
print(gen2(4)) #<generator object gen2 at 0x000001F3A6F31E48>
gen2(4)
for i in gen2(4):
print(i) #0 1 2 3
注意:从对象中取值,要先拿出对象
def test():
yield 1
yield 2
yield 3
print(test())
ta = test() #从对象取值
print(next(ta)) #1
print(next(ta)) #2
print(next(ta)) #3
print(next(test())) #1 加括号是调用函数
print(next(test())) #1
print(next(test())) #1
4.三者关系
可迭代对象:指实现了Python协议,可以通过for...in...循环遍历的对象,比如list、dict、str...、迭代器、生成器
迭代器:可以记住自己遍历位置的对象,直观体现就是可以使用next()函数返回值,迭代器只能往前,不能往后,当遍历完毕后,next()会抛出异常
生成器:是特殊的迭代器,需要注意迭代器不一定是生成器,他是Python提供的通过简便的方法写出迭代器的一种手段
包含关系:可迭代对象>迭代器>生成器