1. 程式人生 > 程式設計 >Javascript生成器(Generator)的介紹與使用

Javascript生成器(Generator)的介紹與使用

什麼是生成器?

生成器是在函式內部執行的一些程式碼

  • 返回值後,它會自行暫停,並且——
  • 呼叫程式可以要求取消暫停並返回另一個值

這種“返回”不是傳統的從函式 return。所以它被賦予了一個特殊的名稱——yield。

生成器語法因語言而異。Javascript 的生成器語法類似於 PHP,但是區別也很大,如果你希望它們的作用相同,那麼最終你會感到非常困惑。

在 javascript 中,如果想要使用生成器,則需要:

  • 定義特殊的生成器函式
  • 呼叫該函式建立一個生成器物件
  • 在迴圈中使用該生成器物件,或直接呼叫其 next 方法

我們以下面這個簡單的程式做為起點,並執行以下每個步驟:

// File: sample-program.js
function *createGenerator() {
 for(let i=0;i<20;i++) {
 yield i
 }
}

const generator = createGenerator()

console.log(generator.next())
console.log(generator.next())

如果執行這段程式碼,則會得到以下輸出:

$ node sample-program.js

{ value: 0,done: false }
{ value: 1,done: false }

下面我來解釋該程式是如何工作的。

生成器函式

首先,程式碼中存在生成器函式的定義:

function* createGenerator() {
 for(let i=0;i<20;i++) {
 yield i
 }
}

function 後面的 * 告訴 javascript 這是一個生成器函式。以下寫法都是生成器函式的有效定義。

function*createGenerator
function* createGenerator
function *createGenerator

* 並不是函式名的一部分。而是 function* 符號定義了生成器。

呼叫生成器函式

定義了生成器函式後,我們將其命名為其他名稱的函式。

// 注意:當呼叫時,沒有 *。 * 不是函式名稱的一部分
// `function *` 是用於定義生成器函式的符號
const generator = createGenerator()

但是要記住:createGenerator 函式沒有返回值。這是因為生成器函式沒有傳統的返回值。相反,當你直接呼叫生成器函式時,它總是返回例項化的 Generator 物件。

這個生成器物件具有一個 next 方法。呼叫 next 將在生成器函式內部執行程式碼。

function* createGenerator() {
 for(let i=0;i<20;i++) {
  yield i
 }
}

這很重要,足以再次呼叫它。直接呼叫生成器函式不會在生成器函式中執行任何程式碼。而是建立一個生成器物件。它在生成器物件上呼叫 next,從而呼叫生成器函式中的程式碼。

首次在生成器物件上呼叫 next 時,內部程式碼將會一直執行,直到出現 yield 語句。一旦執行到 yield,javascript 將會暫停該程式碼的執行,而 next 將返回(即給你,或yield)一個物件,該物件包含 yield 行中的值。

當你第二次(或第三次、第四次甚至更多次)再呼叫 next 時,程式碼將會取消暫停並繼續執行(在上次呼叫時中斷的地方)。變數(例如本例中的 i )將會保持它的值。當代碼到達另一個 yield 語句時,該函式會再次暫停,並返回一個包含 yield 值的物件。

這就是為什麼我們要呼叫兩次 next

console.log(generator.next())
console.log(generator.next())

會得到以下輸出:

{ value: 0,done: false }

生成器函式中的程式碼執行完畢後,將來對 next 的任何呼叫都會返回一個物件,該物件的值為 undefined 且done 設定為 true。

{ value: undefined,done: true }

生成器和迴圈

雖然可以在生成器物件上手動呼叫 next,但我們主要是要在迴圈中使用。看一下這個稍作修改的程式。

// File: sample-program.js
@highlightsyntax@jscript
function *createGenerator() {
 for(let i=0;i<5;i++) {
 yield i
 }
}

const generator = createGenerator()
for(const value of generator) {
 console.log(value)
}

當在 for...of 迴圈中使用生成器物件時,每次迴圈都會在生成器物件上呼叫 next,並用產生的值填充變數(上面的 value)。執行該程式將會輸出以下內容:

$ node sample-program.js
0
1
2
3
4

在下一篇文章中,我們將更深入地探討 for ... of 迴圈,並探索怎樣為 javascript 提供一種內建方法來迴圈 javascript 中的任何物件。

總結

到此這篇關於Javascript生成器(Generator)的文章就介紹到這了,更多相關Javascript生成器(Generator)內容請搜尋我們以前的文章或繼續瀏覽下面的相關文章希望大家以後多多支援我們!