迭代器,生成器畜普,列表生成式

1期丰、列表生成式

舉個(gè)例子,要生成list [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]可以用list(range(1, 11)):

>>> list(range(1, 11))
[1, 2, 3, 4, 5, 6, 7, 8, 9, 10]

但如果要生成[1x1, 2x2, 3x3, ..., 10x10]怎么做?方法一是循環(huán):

>>> L = []
>>> for x in range(1, 11):
...    L.append(x * x)
...
>>> L
[1, 4, 9, 16, 25, 36, 49, 64, 81, 100]

但是循環(huán)太繁瑣钝荡,而列表生成式則可以用一行語句代替循環(huán)生成上面的list:

>>> [x * x for x in range(1, 11)]
[1, 4, 9, 16, 25, 36, 49, 64, 81, 100]

for循環(huán)后面還可以加上if判斷街立,這樣我們就可以篩選出僅偶數(shù)的平方:

>>> [x * x for x in range(1, 11) if x % 2 == 0]
[4, 16, 36, 64, 100]

還可以使用兩層循環(huán),可以生成全排列:

>>> [m + n for m in 'ABC' for n in 'XYZ']
['AX', 'AY', 'AZ', 'BX', 'BY', 'BZ', 'CX', 'CY', 'CZ']

2埠通、迭代器

迭代器是訪問集合元素的一種方式赎离。迭代器對象從集合的第一個(gè)元素開始訪問,直到所有的元素被訪問完結(jié)束端辱。迭代器只能往前不會后退梁剔,不過這也沒什么,因?yàn)槿藗兒苌僭诘局型笸寺邮帧A硗夂镀樱鞯囊淮髢?yōu)點(diǎn)是不要求事先準(zhǔn)備好整個(gè)迭代過程中所有的元素。迭代器僅僅在迭代到某個(gè)元素時(shí)才計(jì)算該元素喷鸽,而在這之前或之后众雷,元素可以不存在或者被銷毀。這個(gè)特點(diǎn)使得它特別適合用于遍歷一些巨大的或是無限的集合做祝,比如幾個(gè)G的文件
特點(diǎn):
1. 訪問者不需要關(guān)心迭代器內(nèi)部的結(jié)構(gòu)砾省,僅需通過next()方法不斷去取下一個(gè)內(nèi)容
2. 不能隨機(jī)訪問集合中的某個(gè)值 ,只能從頭到尾依次訪問
3. 訪問到一半時(shí)不能往回退
4. 便于循環(huán)比較大的數(shù)據(jù)集合混槐,節(jié)省內(nèi)存

>>> a = iter([1,2,3,4,5])
>>> a
<list_iterator object at 0x101402630>
>>> a.__next__()
1
>>> a.__next__()
2
>>> a.__next__()
3
>>> a.__next__()
4
>>> a.__next__()
5
>>> a.__next__()
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
StopIteration

3编兄、 生成器

(1)

一個(gè)函數(shù)調(diào)用時(shí)返回一個(gè)迭代器,那這個(gè)函數(shù)就叫做生成器(generator)声登;如果函數(shù)中包含yield語法狠鸳,那這個(gè)函數(shù)就會變成生成器;

def fun ():
    yield 1
    yield 2
    yield 3
    yield 4

上述代碼中:func是函數(shù)稱為生成器悯嗓,當(dāng)執(zhí)行此函數(shù)func()時(shí)會得到一個(gè)迭代器件舵。

>>> fun
<function fun at 0x000001B3528A7158>
>>> fun()
<generator object fun at 0x000001B3528A56D0>
>>> temp = fun()
>>> temp.__next__()
1
>>> 
KeyboardInterrupt
>>> temp.__next__()
2
>>> temp.__next__()
3
>>> temp.__next__()
4
>>> temp.__next__()
Traceback (most recent call last):
  File "<pyshell#13>", line 1, in <module>
    temp.__next__()
StopIteration

(2)

要?jiǎng)?chuàng)建一個(gè)generator,有很多種方法脯厨。第一種方法很簡單铅祸,只要把一個(gè)列表生成式的[]改成(),就創(chuàng)建了一個(gè)generator:

>>> L = [x * x for x in range(10)]
>>> L
[0, 1, 4, 9, 16, 25, 36, 49, 64, 81]
>>> g = (x * x for x in range(10))
>>> g
<generator object <genexpr> at 0x1022ef630>

創(chuàng)建L和g的區(qū)別僅在于最外層的[]和()合武,L是一個(gè)list临梗,而g是一個(gè)generator。

我們可以直接打印出list的每一個(gè)元素稼跳,但我們怎么打印出generator的每一個(gè)元素呢盟庞?

如果要一個(gè)一個(gè)打印出來,可以通過next()函數(shù)獲得generator的下一個(gè)返回值:

>>> next(g)
0
>>> next(g)
1
>>> next(g)
4
>>> next(g)
9
>>> next(g)
16
>>> next(g)
25
>>> next(g)
36
>>> next(g)
49
>>> next(g)
64
>>> next(g)
81
>>> next(g)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
StopIteration

我們講過汤善,generator保存的是算法茫经,每次調(diào)用next(g)巷波,就計(jì)算出g的下一個(gè)元素的值,直到計(jì)算到最后一個(gè)元素卸伞,沒有更多的元素時(shí)抹镊,拋出StopIteration的錯(cuò)誤。

當(dāng)然荤傲,上面這種不斷調(diào)用next(g)實(shí)在是太變態(tài)了垮耳,正確的方法是使用for循環(huán),因?yàn)間enerator也是可迭代對象:

>>> g = (x * x for x in range(10))
>>> for n in g:
...     print(n)
... 
0
1
4
9
16
25
36
49
64
81

所以遂黍,我們創(chuàng)建了一個(gè)generator后终佛,基本上永遠(yuǎn)不會調(diào)用next(),而是通過for循環(huán)來迭代它雾家,并且不需要關(guān)心StopIteration的錯(cuò)誤铃彰。

編寫斐波拉契數(shù)列:
。芯咧。牙捉。

4、實(shí)例

a敬飒、利用生成器自定義range

def nrange(num):
    temp = -1
    while True:
        temp = temp + 1
        if temp >= num:
            return
        else:
            yield temp

b邪铲、利用迭代器訪問range
...

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末,一起剝皮案震驚了整個(gè)濱河市无拗,隨后出現(xiàn)的幾起案子带到,更是在濱河造成了極大的恐慌,老刑警劉巖英染,帶你破解...
    沈念sama閱讀 219,490評論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件揽惹,死亡現(xiàn)場離奇詭異,居然都是意外死亡四康,警方通過查閱死者的電腦和手機(jī)永丝,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,581評論 3 395
  • 文/潘曉璐 我一進(jìn)店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來箭养,“玉大人,你說我怎么就攤上這事哥牍”厦冢” “怎么了?”我有些...
    開封第一講書人閱讀 165,830評論 0 356
  • 文/不壞的土叔 我叫張陵嗅辣,是天一觀的道長撼泛。 經(jīng)常有香客問我,道長澡谭,這世上最難降的妖魔是什么愿题? 我笑而不...
    開封第一講書人閱讀 58,957評論 1 295
  • 正文 為了忘掉前任,我火速辦了婚禮,結(jié)果婚禮上潘酗,老公的妹妹穿的比我還像新娘杆兵。我一直安慰自己,他們只是感情好仔夺,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,974評論 6 393
  • 文/花漫 我一把揭開白布琐脏。 她就那樣靜靜地躺著,像睡著了一般缸兔。 火紅的嫁衣襯著肌膚如雪日裙。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 51,754評論 1 307
  • 那天惰蜜,我揣著相機(jī)與錄音昂拂,去河邊找鬼。 笑死抛猖,一個(gè)胖子當(dāng)著我的面吹牛格侯,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播樟结,決...
    沈念sama閱讀 40,464評論 3 420
  • 文/蒼蘭香墨 我猛地睜開眼养交,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了瓢宦?” 一聲冷哼從身側(cè)響起碎连,我...
    開封第一講書人閱讀 39,357評論 0 276
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎驮履,沒想到半個(gè)月后鱼辙,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,847評論 1 317
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡玫镐,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,995評論 3 338
  • 正文 我和宋清朗相戀三年倒戏,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片恐似。...
    茶點(diǎn)故事閱讀 40,137評論 1 351
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡杜跷,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出矫夷,到底是詐尸還是另有隱情葛闷,我是刑警寧澤,帶...
    沈念sama閱讀 35,819評論 5 346
  • 正文 年R本政府宣布双藕,位于F島的核電站淑趾,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏忧陪。R本人自食惡果不足惜扣泊,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,482評論 3 331
  • 文/蒙蒙 一近范、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧延蟹,春花似錦评矩、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,023評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至俯萌,卻和暖如春果录,著一層夾襖步出監(jiān)牢的瞬間,已是汗流浹背咐熙。 一陣腳步聲響...
    開封第一講書人閱讀 33,149評論 1 272
  • 我被黑心中介騙來泰國打工弱恒, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留,地道東北人棋恼。 一個(gè)月前我還...
    沈念sama閱讀 48,409評論 3 373
  • 正文 我出身青樓返弹,卻偏偏與公主長得像,于是被迫代替她去往敵國和親爪飘。 傳聞我的和親對象是個(gè)殘疾皇子义起,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,086評論 2 355

推薦閱讀更多精彩內(nèi)容