列表生成式、生成器、叠代器。
阿新 • • 發佈:2017-11-12
err 需要 end 每一個 可叠代對象 生成式 ner 大量 dir ,而是通過
列表生成式,需求把列表[0,1,2,3,4,5,6,7,8,9]每一個元素加1。
#列表生成式 list generration #第一種方法 a = [0,1,2,3,4,5,6,7,8,9] b = [] for i in a: b.append(i+1) print(b) #第二種方法 c = [i+1 for i in a] print(c) #第三種方法 for index,i in enumerate(a): a[index] +=1 print(a)
#通過列表生成式,我們可以直接創建一個列表。但是,受到內存限制,列表容量肯定是有限的。而且,創建一個包含100萬個元素的列表,不僅占用很大的存儲空間,如果我們僅僅需要訪問前面幾個元素,那後面絕大多數元素占用的空間都白白浪費了。
生成器 如果列表元素可以按照某種算法推算出來,那我們是否可以在循環的過程中不斷推算出後續的元素呢?這樣就不必創建完整的list,從而節省大量的空間。在Python中,這種一邊循環一邊計算的機制,稱為生成器:generator。
要創建一個generator,有很多種方法。第一種方法很簡單,只要把一個列表生成式的[]
改成()
,就創建了一個generator:
L = [i*2 for i in range(10)] #列表生成式 print(L) g = (i*2 for i inrange(10)) #創建一個生成器,僅僅把列表中括號改成小括號。 print(g) g.__next__()
1、生成器只有在調用的時候才會產生數據。
2、生成器取值只能往後取值,不能跨步取值和後退取值。
g = (i*2 for i in range(10)) #創建一個生成器,僅僅把列表中括號改成小括號。 print(g.__next__()) #一般不采用此種方法進行調用,如果調用值超過了生成器的值那麽分出現報錯。 for n in g: #使用for循環進行調用並且不會出現超出值而報錯。 print(n)
我們創建了一個generator後,基本上永遠不會調用next()
for
循環來叠代它,並且不需要關心StopIteration
的錯誤。
generator非常強大。如果推算的算法比較復雜,用類似列表生成式的for
循環無法實現的時候,還可以用函數來實現。
比如,著名的斐波拉契數列(Fibonacci),除第一個和第二個數外,任意一個數都可由前兩個數相加得到:
def fib(max): n,a,b, = 0,0,1 while n <max: #print(b) #這種方式還不叫生成器,距離生成器只有一步之遙了。 yield (b) a,b = b,a+b n = n+1
returan "------none-----" g = fib(10) #給以給生成器賦值進行調用。 for i in g: print(i)
如果執行報StopIteration可以用下面這段代碼進行抓錯。
while True: try: x =next(g) #此處會去調用生成器一直調用到出錯會被下面的except給抓到 print("g",x) except StopIteration as e: #只有當報StopIteration as(賦名)給 e print("Generrator return value",e.value) break
叠代器
可以直接作用於for
循環的數據類型有以下幾種:
一類是集合數據類型,如list
、tuple
、dict
、set
、str
等;
一類是generator
,包括生成器和帶yield
的generator function。
這些可以直接作用於for
循環的對象統稱為可叠代對象:Iterable
。
可以使用isinstance()
判斷一個對象是否是Iterable
對象:.
a = [1,2,3] print(dir(a)) #用內置函數可以查看可用的調用方式。 from collections import Iterable #判斷是否為叠代器對象 print(isinstance([],Iterable)) #判斷是否為叠代器對象 #輸出結果 True print(isinstance([-1,0,1],Iterable))#判斷是否為叠代器對象 #輸出結果 True print(isinstance(0,Iterable))#判斷是否為叠代器對象 #輸出結果 False from collections import Iterator #判斷是否為叠代器 print(isinstance([x for x in range(5)],Iterator)) #判斷是否為叠代器 #輸出結果 False print(isinstance(iter([x for x in range(5)]),Iterator)) #判斷是否為叠代器 #輸出結果
列表生成式、生成器、叠代器。