python迭代器
1. 可迭代對象
可以利用 for 循環(huán)的對象,都叫可迭代對象。
列表、元組、字典、字符串等都是可迭代對象。
# 以列表為例
>>> alist = [0, 1, 2, 3, 4, 5]
>>> for i in alist:
... print(i)
...
0
1
2
3
4
5
2. 是否可迭代?
對 Python 比較熟悉的朋友,肯定知道哪些數(shù)據(jù)類型是可迭代的,哪些是不可迭代的。
但是對新手來說,可能需要借助一些函數(shù)來判別,比如 Python 內(nèi)置的 collections.abc
模塊,這個模塊只有在 Python 中才有噢,在這個模塊中提供了一個 Iterable 類,可以用 isinstance 來判斷。
>>> from collections.abc import Iterable
>>>
>>> isinstance([0, 1, 2], Iterable) # 列表
True
>>> isinstance({"name": "張三"}, Iterable) # 字典
True
>>> isinstance((1,2,3), Iterable) # 元組
True
>>> isinstance("hello", Iterable) # 字符串
True
但是這種方法并不是百分百準(zhǔn)確(具體下面會說到),最準(zhǔn)確的方法,還是應(yīng)該使用 for 循環(huán)。
3. 可迭代協(xié)議
可迭代對象內(nèi)部是如何實現(xiàn)在你對其進(jìn)行 for 循環(huán)時,可以一個一個元素的返回出來呢?
這就要談到迭代器協(xié)議。
第一種場景:如果一個對象內(nèi)部實現(xiàn)了 __iter__()
方法 ,并返回一個迭代器實例,那么該對象就是可迭代對象
class Array:
mylist = [0,1,2]
# 返回迭代器類的實例
def __iter__(self):
return iter(self.mylist)
# 得到可迭代對象
my_list = Array()
print(isinstance(my_list, Iterable)) # True
for i in my_list:
print(i)
第二種場景:假設(shè)一個對象沒有實現(xiàn) __iter__()
,Python 解釋器 __getitem__()
方法獲取元素,如果可行,那么該對象也是一個可迭代對象。
from collections.abc import Iterable
class Array:
mylist = [0,1,2]
def __getitem__(self, item):
return self.mylist[item]
# 得到一個可迭代對象
my_list = Array()
print(isinstance(my_list, Iterable)) # False
for i in my_list:
print(i)
此時如果你使用 isinstance(my_list, Iterable)
去判斷是否是可迭代,就會返回 False,因為 isinstance 這種方法就是檢查對象是否有 __iter__
方法。這也論證了使用 isinstance(my_list, Iterable)
去判斷是否可迭代是不準(zhǔn)確的。
4. 什么是迭代器
當(dāng)你對一個可迭代對象使用 iter 函數(shù)后,它會返回一個迭代器對象,對于迭代器對象,我們可以使用 next 函數(shù),去獲取元素,每執(zhí)行一次,獲取一次,等到全部獲取完畢,會拋出 StopIteration 提示無元素可取。
>>> alist = [0, 1, 2, 3]
>>> gen = iter(alist)
>>> gen
>>> next(gen)
0
>>> next(gen)
1
>>> next(gen)
2
>>> next(gen)
3
>>> next(gen)
Traceback (most recent call last):
File "", line 1, in
StopIteration
5. 迭代器協(xié)議
對比可迭代對象,迭代器
的內(nèi)部只是多了一個函數(shù)而已 – __next__()
正因為有了它,我們才可以用 next 來獲取元素。
迭代器,是在可迭代的基礎(chǔ)上實現(xiàn)的。要創(chuàng)建一個迭代器,我們首先,得有一個可迭代對象。 現(xiàn)在就來看看,如何創(chuàng)建一個可迭代對象,并以可迭代對象為基礎(chǔ)創(chuàng)建一個迭代器。
from collections.abc import Iterator
class Array:
index = 0
mylist = [0,1,2]
# 返回該對象的迭代器類的實例
# 因為自己就是迭代器,所以返回self
def __iter__(self):
return self
# 當(dāng)無元素時,必要拋出 StopIteration
def __next__(self):
if self.index <= len(self.mylist)-1:
value = self.mylist[self.index]
self.index += 1
return value
raise StopIteration
my_iterator = iter(Array())
print(isinstance(my_iterator, Iterator)) # output: True
print(next(my_iterator)) # output: 0
print(next(my_iterator)) # output: 1
print(next(my_iterator)) # output: 2
print(next(my_iterator)) # StopIteration
審核編輯:符乾江
-
python
+關(guān)注
關(guān)注
56文章
4809瀏覽量
85069 -
迭代器
+關(guān)注
關(guān)注
0文章
44瀏覽量
4350
發(fā)布評論請先 登錄
相關(guān)推薦
Python Connector for InterBase連接解決方案
適用于MySQL和MariaDB的Python連接器:可靠的MySQL數(shù)據(jù)連接器和數(shù)據(jù)庫
![適用于MySQL和MariaDB的<b class='flag-5'>Python</b>連接<b class='flag-5'>器</b>:可靠的MySQL數(shù)據(jù)連接<b class='flag-5'>器</b>和數(shù)據(jù)庫](https://file1.elecfans.com/web3/M00/06/57/wKgZPGeJ2kmAcWpWAAAh1ecL_LM122.png)
Triton編譯器安裝步驟詳解
Python中代理服務(wù)器的配置與應(yīng)用
Python代理技術(shù)詳解:從入門到進(jìn)階
使用Python構(gòu)建高效的HTTP代理服務(wù)器
pytorch和python的關(guān)系是什么
opencv-python和opencv一樣嗎
用pycharm進(jìn)行python爬蟲的步驟
如何用python調(diào)用瀏覽器的視頻?
python解析netflow數(shù)據(jù)到csv的流程詳解
![<b class='flag-5'>python</b>解析netflow數(shù)據(jù)到csv的流程<b class='flag-5'>詳解</b>](https://file1.elecfans.com/web2/M00/D9/FE/wKgaomYpzAiAPrQGAABVCN7G14M811.png)
HFSS不能使用迭代求解
基于Python的地圖繪制教程
![基于<b class='flag-5'>Python</b>的地圖繪制教程](https://file1.elecfans.com/web2/M00/C0/F4/wKgZomXb72KADq8JAABAFRaefm0918.png)
評論