python之產生器-generator

來源:互聯網
上載者:User

標籤:yield   producing   ret   線程   zhang   部落格   原來   數組   角度   

  在跟著廖雪峰的部落格學習python,看到產生器這一章節的時候,首先提到了generator 、yield,然後在搜尋資料的時候,又查到了協程這一概念,這篇文章總結一下這幾個概念.

  generator  從字面上理解,就是產生器,它的實現方式有兩種:

1、不同於清單產生器([]),而是用 ()來表示。(原來這種叫做產生器運算式哦,哈哈)

   訪問方式,可以用for 迴圈來訪問,也可以用 .next 來訪問。

N = [‘Hello‘, ‘World‘, 18, ‘Apple‘, ‘None‘]hh = (s.lower() for s in N if isinstance(s,str) ==True)print hh#for item in hh:#    print item#print hh.next()#print hh.next()#print hh.next()#print hh.next()

輸出結果

<generator object <genexpr> at 0x7f543a074690>
hello
world
apple
none

hh 是產生器返回的值,類似於一個數組。支援 for逐一查看和 .next()訪問,有一點需要注意的是,for 迴圈執行完了之後就不能執行 hh.next()了,類似於指標到了最後,或者C++中迭代器指向了最後,再訪問就會出現錯誤。

2、用yield來產生 ,(叫做產生器函數)

無論用next() 和for 迴圈來調用,都是執行到了yield之後,返回 n值,然後將當前的狀態掛起,然後返回。

def create_counter(n):    print "create counter"    #while True:    while False:        yield n        print ‘increment n‘        n += 1cnt = create_counter(2)#print cntfor item in cnt:    print item#print next(cnt)#print next(cnt)#print cnt.next()#print cnt.next()   

比如這個例子中,當列印cnt的時候,<generator object create_counter at 0x7fa992b8d6e0>

說明這是一個,產生器。
當 為False的時候,只會列印 create counter

當為True的時候,用for 迴圈就會出現死迴圈的情況。

協程:

我知道有進程、線程的概念,但是協程是什麼東西,我還真是不知道

從技術的角度來說,“協程就是你可以暫停執行的函數”。如果你把它理解成“就像產生器一樣”,那麼你就想對了。這是在一篇文章上看到的。

python之所以執行效率高

1、為子程式切換不是線程切換,而是由程式自身控制,因此,沒有線程切換的開銷,和多線程比,線程數量越多,協程的效能優勢就越明顯。

2、執行的過程中不會涉及到鎖機制。

 附一個簡單的生產者和消費者的例子:

def consumer():    r = ‘‘    while True:        n = yield r        if not n:            return        print(‘[CONSUMER] Consuming %s...‘ % n)        time.sleep(1)        r = ‘200 OK‘def produce(c):    c.next()    n = 0    while n < 5:        n = n + 1        print(‘[PRODUCER] Producing %s...‘ % n)        r = c.send(n)        print(‘[PRODUCER] Consumer return: %s‘ % r)    c.close()if __name__==‘__main__‘:    c = consumer()    produce(c)

1. consumer函數是一個generator。 
2. c.send(None)其實等價於next(c),第一次執行時其實只執行到n = yield r就停止了,然後把r的值返回給調用者。 
3. yield r是一個運算式,通過send(msg)被賦值,而send(msg)是有傳回值的,傳回值為:下一個yield r運算式的參數,即為r。 
4. produce一旦生產了東西,通過c.send(n)切換到consumer執行。consumer通過yield拿到訊息,處理,又通過yield把結果傳回。也就是說,c.send(1) 不但會給 c 傳送一個資料,它還會等著下次 yield 從 c 中返回一個資料,它是有傳回值的,一去一回才算完,拿到了返回的資料(200 OK)才繼續下面執行。 
5. 整個流程無鎖,由一個線程執行,produce和consumer協作完成任務,所以稱為“協程”,而非線程的搶佔式多任務。

總結來說,就是 yield r 是一個運算式,通過 c.send 被賦值,然後傳回值為下一個為yield r 運算式的參數。

 

github路徑:https://github.com/billzhangjingle/learnPython/basic/generator.py

在學習的時候搜尋到的相關部落格:

http://python.jobbole.com/86069/

http://python.jobbole.com/86481/

http://www.cnblogs.com/gide/p/6187080.html

http://www.liaoxuefeng.com/wiki/001374738125095c955c1e6d8bb493182103fac9270762a000/0013868328689835ecd883d910145dfa8227b539725e5ed000

http://www.cnblogs.com/cotyb/p/5260032.html

python之產生器-generator

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.