Co流程流程控制器源碼與理解,index.js包含理解和註釋git
這個版本是重點是理解generator工做原理github
// @flow /** * Created by Freax on 16-12-12. * @Blog http://www.myfreax.com/ */ function co(generator) { let gen = generator(); next(gen.next()); //遞歸遍歷generator.next function next(result) { if (result.done)return null;//若是generator執行完畢,直接解決退出遍歷 let res = gen.next(result.value); next(res); } } co(function *gen() { let a = yield 1; console.info(a, 'a'); let b = yield 2; console.info(b, 'b'); let c = yield 3; console.info(c, 'c'); });
理解generator+promise如何工做promise
// @flow /** * Created by Freax on 16-12-12. * @Blog http://www.myfreax.com/ */ function isPromise(obj) { return typeof obj === 'object' && 'function' == typeof obj.then; } function co(generator) { return new Promise((resolve,reject)=>{ let gen = generator(); next(gen.next()); function next(result) { if (result.done)return resolve(result.value);//若是generator執行完畢,直接解決退出遍歷 //判斷是不是Promise,若是是promise則執行promise再進入next遞歸遍歷generator.next if (isPromise(result.value))return result.value.then(res => { let result; try { result = gen.next(res); //拋出generator的錯誤 }catch (e){ return reject(e);// 捕獲後由交給promise處理返回外部處理 } next(result) }, err => { let result; try { result = gen.throw(err); //yield返回promise進入reject後的錯誤,拋出generator的錯誤 }catch (e){ return reject(e); // 捕獲後由交給promise處理返回外部處理 } next(result) }); let res = gen.next(result.value); next(res); } }); } co(function *gen() { let a = yield Promise.resolve(1); console.info(a, 'a'); let b = yield 2; console.info(b, 'b'); let c = yield 3; console.info(c, 'c'); }).catch((err)=>{ console.info(err); });