思考:python
首先思考這樣一個問題:函數
建立一個列表,可是內存受限,容量必定是有限的。那麼若是建立了一個包含100萬個元素的列表,不只佔用很大的存儲空間,而咱們僅僅須要訪問前面幾個元素,那後面絕大多數元素佔用的空間都白白浪費了?spa
這個時候就須要一個容器,在咱們須要數據的時候拿出來,不取數據的時候就釋放掉。這樣就可以節省資源和空間。code
yield的做用:blog
把一個函數變成一個生成器,起到一個延遲的做用,在須要的時候產生結果,節省資源。與聲明一個序列相比,生成器在不使用的時候不佔用內存。內存
一、首先實現一個功能,建立一個列表,而後挨個取出其中的元素。資源
def getNum(n): i = 0 while i < n: print(i) i += 1 getNum(5)
二、在這個基礎上添加一個功能,每次調用這個函數都要返回一個值。get
可是加入return以後整個函數就退出了,下次再使用這個須要須要從頭開始,那能不能實現接着上次停掉的地方開始呢?class
def getNum(n): i = 0 while i < n: return i i += 1 a = getNum(5)
print(a)
三、yeild。若是暫時想不明白,就把它當作return,但與return不一樣的是返回一個值並不會退出函數,而是停在這,直到下次被喚醒。容器
yield與return返回相同的值,區別在於return返回後,函數狀態終止,而yield會保存當前函數的執行狀態,再次調用時,函數又回到以前保存的狀態繼續執行。
可是,若是直接print,發現返回的是一個內存地址。並非咱們想象的那個東西。
此時,對應於生成器的使用有一個專門的關鍵字next,就是至關於告訴生成器往下走一步。直至結束
def getNum(n): i = 0 while i < n: yield i i += 1 a = getNum(5)
print(a)
##調用生成器的兩種方式
print(next(a))
print(a.__next__)
最後,那麼這個生成器有什麼用呢?加入你有100萬張圖像,而每次你都只取n張,下次再取的時候接着剛剛的序列繼續取。
那麼它是如何實現節省內存的呢?只記住當前位置,生成器只保留一個值,next以後上一個值就沒有了,這就是爲何它能接着上次中止的位置繼續下去!