这是我参与8月更文挑战的第二十九天,活动详情查看:8月更文挑战”
JavaScript进阶(七)call, apply, bind
写在前面,generator对于写react的同学相信是相对熟悉一点。react的中间件,react-saga就充分用到的这个 数据类型。废话少说,Let's go!
Generator 实现
generator(生成器)是ES6标准引入的新的数据类型。generator看上去就像是平常用到的函数,它可以返回多次,和 Promise ⼀样,也可以⽤来异步编程。其借鉴了Python的generator的概念和语法。当然你了解Python的generator,相信这个对你来说肯定是相当简单。
// * 表示这是⼀个 Generator 函数
// 通过 yield 暂停代码
// 调⽤ next 恢复执⾏
function* test() {
let add = 1 + 2;
yield 2;
yield 3;
}
let b = test();
console.log(b.next()); // > { value: 2, done: false }
console.log(b.next()); // > { value: 3, done: false }
console.log(b.next()); // > { value: undefined, done: true }
从以上代码可以发现,该函数执⾏后拥有了 next 函数,执⾏后返回了⼀个对象。调⽤ next 函数的时候,运行yield前面的代码,输出yield后面的结果,然后暂停的代码,再调用,在暂停,最后执行完所有的yield结束。以下是 Generator 函数的简单实现
// cb 编译过的 test 函数
function generator(cb) {
return (function () {
var object = {
next: 0,
stop: function () {
}
};
return {
next: function () {
var ret = cb(object);
if (ret === undefined) return {value: undefined, done: true};
return {
value: ret,
done: false
};
}
};
})();
}
// 如果你使⽤ babel 编译后可以发现 test 函数变成了这样
function test() {
var a;
return generator(function (_context) {
while (1) {
switch ((_context.prev = _context.next)) {
// 可以发现通过 yield 将代码分割成⼏块
// 每次执⾏ next 函数就执⾏⼀块代码
// 并且表明下次需要执⾏哪块代码
case 0:
a = 1 + 2;
_context.next = 4;
return 2;
case 4:
_context.next = 6;
return 3;
// 执⾏完毕
case 6:
case "end":
return _context.stop();
}
}
});
}
好,今天就到这里了,明天见。 我是Augus,一个爱瞎搞的软件开发工程师。 END~~~