python中yield用法詳解

      今天看python學習視頻學到生成器這一塊時始終弄不懂yield的用法及其原理,在網上詳細查看yield的用法以後總結一下yield的使用方法。python

      先看一個簡單的yield語句:函數

def fib(max):
    n, a, b = 0, 0, 1
    while n < max:
        yield b
        a, b = b, a + b
        n = n + 1

      這是有關斐波那契數列的一個函數,當時正是這個函數中的yield使我困惑致使整個函數不能理解。這個函數包含yield,實際上這已是一個生成器(generator)了,這與普通的函數有很大的不一樣。學習

def h():
    print 'hello'
    yield 6
h()

      能夠看到,調用h()以後,print 語句並無執行!這就是yield,那麼,如何讓print 語句執行呢?這就是後面要討論的問題,經過後面的討論和學習,就會明白yield的工做原理了。spa

2. yield是一個表達式code

      Python2.5之前,yield是一個語句,但如今2.5中,yield是一個表達式(Expression),好比:視頻

      x = yield 6blog

表達式(yield 6)的返回值將賦值給x,因此,認爲 x = 5 是錯誤的。那麼如何獲取(yield 5)的返回值呢?須要用到後面要介紹的send(msg)方法。generator

3. 透過next()語句看原理io

      如今,咱們來揭曉yield的工做原理。咱們知道,咱們上面的h()被調用後並無執行,由於它有yield表達式,所以,咱們經過next()語句讓它執行。next()語句將恢復Generator執行,並直到下一個yield表達式處。好比:ast

def h():
    print('hello')
    yield 6
    print('python!')
c = h()
c.__next__()       #這裏是雙下劃線

      c.next()調用後,h()開始執行,直到遇到yield 6,所以輸出結果:

      hello

當咱們再次調用c.next()時,會繼續執行,直到找到下一個yield表達式。因爲後面沒有yield了,所以會拋出異常:

hello
Traceback (most recent call last):
python!
  File "C:/Users/zxj/PycharmProjects/firstProject/day4/test.py", line 29, in <module>
    c.__next__()
StopIteration

4. send(msg) 與 next()

      瞭解了next()如何讓包含yield的函數執行後,咱們再來看另一個很是重要的函數send(msg)。其實next()和send()在必定意義上做用是類似的,區別是send()能夠傳遞yield表達式的值進去,而next()不能傳遞特定的值,只能傳遞None進去。所以,咱們能夠看作

c.next() 和 c.send(None) 做用是同樣的。

來看這個例子: 

def h():
    print('hello'),
    x = yield 6
    print m
    y = yield 23
    print 'python'
c = h()
c.__next__()  #至關於c.send(None)
c.send('ok')  #(yield 6)表達式被賦予了'ok'

輸出的結果爲:

hello

ok

      須要提醒的是,第一次調用時,請使用next()語句或是send(None),不能使用send發送一個非None的值,不然會出錯的,由於沒有yield語句來接收這個值。

5. send(msg) 與 next()的返回值

      send(msg) 和 next()是有返回值的,它們的返回值很特殊,返回的是下一個yield表達式的參數。好比yield 6,則返回 6 。到這裏,是否是明白了一些什麼東西?咱們再延續上面的例子:

def h():
    print('hello')
    x = yield 6
    print(m)
    y = yield 23
    print (y)
c = h()
x = c.__next__()  #x 獲取了yield 6 的參數值 6
y = c.send('ok')  #y 獲取了yield 23 的參數值23
print(x,y)

      輸出結果:

hello
ok
6 23

      以上就是python中有關yield用法方面的總結,若有不對的地方或者不全面的地方歡迎你們批評指正!!!

相關文章
相關標籤/搜索