ES6 Generator 函式介紹
ES6 新引入了 Generator 函式,可以透過 yield 關鍵字,把函式的執行流掛起,為改變執行流程提供了可能,從而為非同步程式設計提供解決方案。 |
Generator 有兩個區分於普通函式的部分:
- 一是在 function 後面,函式名之前有個 * ;
- 函式內部有 yield 表示式。
其中 * 用來表示函式為 Generator 函式,yield 用來定義函式內部的狀態。
function* func(){ console.log("one"); yield '1'; console.log("two"); yield '2'; console.log("three"); return '3'; }
呼叫 Generator 函式和呼叫普通函式一樣,在函式名後面加上()即可,但是 Generator 函式不會像普通函式一樣立即執行,而是返回一個指向內部狀態物件的指標,所以要呼叫遍歷器物件Iterator 的 next 方法,指標就會從函式頭部或者上一次停下來的地方開始執行。
f.next(); // one // {value: "1", done: false} f.next(); // two // {value: "2", done: false} f.next(); // three // {value: "3", done: true} f.next(); // {value: undefined, done: true}
第一次呼叫 next 方法時,從 Generator 函式的頭部開始執行,先是列印了 one ,執行到 yield 就停下來,並將yield 後邊表示式的值 '1',作為返回物件的 value 屬性值,此時函式還沒有執行完, 返回物件的 done 屬性值是 false。
第二次呼叫 next 方法時,同上步 。
第三次呼叫 next 方法時,先是列印了 three ,然後執行了函式的返回操作,並將 return 後面的表示式的值,作為返回物件的 value 屬性值,此時函式已經結束,多以 done 屬性值為true 。
第四次呼叫 next 方法時, 此時函式已經執行完了,所以返回 value 屬性值是 undefined ,done 屬性值是 true 。如果執行第三步時,沒有 return 語句的話,就直接返回 {value: undefined, done: true}。
一般情況下,next 方法不傳入引數的時候,yield 表示式的返回值是 undefined 。當 next 傳入引數的時候,該引數會作為上一步yield的返回值。
function* sendParameter(){ console.log("strat"); var x = yield '2'; console.log("one:" + x); var y = yield '3'; console.log("two:" + y); console.log("total:" + (x + y)); }
next不傳參
var sendp1 = sendParameter(); sendp1.next(); // strat // {value: "2", done: false} sendp1.next(); // one:undefined // {value: "3", done: false} sendp1.next(); // two:undefined // total:NaN // {value: undefined, done: true}
ext傳參
var sendp2 = sendParameter(); sendp2.next(10); // strat // {value: "2", done: false} sendp2.next(20); // one:20 // {value: "3", done: false} sendp2.next(30); // two:30 // total:50 // {value: undefined, done: true}
除了使用 next ,還可以使用 for... of 迴圈遍歷 Generator 函式生產的 Iterator 物件。
return 方法返回給定值,並結束遍歷 Generator 函式。
return 方法提供引數時,返回該引數;不提供引數時,返回 undefined 。
function* foo(){ yield 1; yield 2; yield 3; } var f = foo(); f.next(); // {value: 1, done: false} f.return("foo"); // {value: "foo", done: true} f.next(); // {value: undefined, done: true} throw 方法 throw 方法可以再 Generator 函式體外面丟擲異常,再函式體內部捕獲。 var g = function* () { try { yield; } catch (e) { console.log('catch inner', e); } }; var i = g(); i.next(); try { i.throw('a'); i.throw('b'); } catch (e) { console.log('catch outside', e); } // catch inner a // catch outside b
遍歷器物件丟擲了兩個錯誤,第一個被 Generator 函式內部捕獲,第二個因為函式體內部的catch 函式已經執行過了,不會再捕獲這個錯誤,所以這個錯誤就丟擲 Generator 函式體,被函式體外的 catch 捕獲。
yield* 表示式表示 yield 返回一個遍歷器物件,用於在 Generator 函式內部,呼叫另一個 Generator 函式。
function* callee() { console.log('callee: ' + (yield)); } function* caller() { while (true) { yield* callee(); } } const callerObj = caller(); callerObj.next(); // {value: undefined, done: false} callerObj.next("a"); // callee: a // {value: undefined, done: false} callerObj.next("b"); // callee: b // {value: undefined, done: false} // 等同於 function* caller() { while (true) { for (var value of callee) { yield value; } } }
為不具備 Iterator 介面的物件提供遍歷方法。
function* objectEntries(obj) { const propKeys = Reflect.ownKeys(obj); for (const propKey of propKeys) { yield [propKey, obj[propKey]]; } } const jane = { first: 'Jane', last: 'Doe' }; for (const [key,value] of objectEntries(jane)) { console.log(`${key}: ${value}`); } // first: Jane // last: Doe
Reflect.ownKeys() 返回物件所有的屬性,不管屬性是否可列舉,包括 Symbol。
jane 原生是不具備 Iterator 介面無法透過 for... of遍歷。這邊用了 Generator 函式加上了 Iterator 介面,所以就可以遍歷 jane 物件了。
原文地址:
來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/31559985/viewspace-2694667/,如需轉載,請註明出處,否則將追究法律責任。
相關文章
- javascript中generator函式的介紹JavaScript函式
- ES6 Generator函式函式
- ES6中的迭代器、Generator函式以及Generator函式的非同步操作函式非同步
- ES6生成器函式generator函式
- 探索es6系列之—-Generator生成器函式函式
- ORACLE函式介紹Oracle函式
- TypeScript 函式介紹TypeScript函式
- stoi函式介紹函式
- JavaScript Generator 函式JavaScript函式
- ES6設定函式預設引數簡單介紹函式
- ES6的Generator函式(2018-06-21)函式
- oracle常用函式介紹Oracle函式
- 機器學習基本函式介紹機器學習函式
- replaceChild()函式用法介紹函式
- lpad函式介紹函式
- oracle REPLACE 函式 介紹Oracle函式
- oracle 日期函式介紹Oracle函式
- CUDA常用函式介紹函式
- Trim() 函式的介紹函式
- GCD、dispatch 函式介紹GC函式
- cuda函式庫介紹函式
- 【函式】Oracle TRIM函式語法介紹函式Oracle
- Generator 函式的使用函式
- 函式表示式和函式宣告簡單介紹函式
- Dart建構函式介紹Dart函式
- javascript函式中with的介紹JavaScript函式
- funclib函式庫介紹函式
- 網路常用函式介紹函式
- Oracle 的基本函式介紹Oracle函式
- prototype.js函式介紹JS函式
- ES6-Generator 函式 和 async 函式函式
- 生成器函式generator函式
- Generator函式語法解析函式
- 深入理解 Generator 函式函式
- Signal ()函式詳細介紹 Linux函式函式Linux
- ORACLE函式介紹第三篇 著名函式之聚合函式Oracle函式
- ORACLE函式介紹第六篇 著名函式之分析函式Oracle函式
- 原創:oracle聚合函式介紹Oracle函式