Last active
June 17, 2018 11:32
-
-
Save SwimmingTiger/742aa221bb3a7eb61664a06f48960d71 to your computer and use it in GitHub Desktop.
关于生成器函数和async/await的区别与联系的DEMO
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
function now() { | |
var d = new Date(); | |
return ('0' + d.getHours()).substr(-2) + ':' + ('0' + d.getMinutes()).substr(-2) + ':' + ('0' + d.getSeconds()).substr(-2); | |
} | |
function sleep(t, n) { | |
return new Promise(function (resolve) { | |
console.log('begin: ' + n + ' sleep ' + t + 'ms, ' + now()); | |
setTimeout(function () { | |
console.log('end: ' + n + ' slept ' + t + 'ms, ' + now()); | |
resolve(); | |
}, t); | |
}); | |
} | |
async function asyncFunc(n) { | |
await sleep(2000, n); | |
await sleep(3000, n); | |
} | |
function* gen(n) { | |
yield sleep(2000, n); | |
yield sleep(3000, n); | |
} | |
function spawn1(g) { | |
var r = g.next('spawn1'); | |
if (r.value != undefined) { | |
r.value.then(function () { | |
spawn1(g); | |
}); | |
} | |
} | |
function spawn2(g) { | |
var pool = []; | |
for (var r=g.next('spawn2'); r.value!=undefined; r=g.next('spawn2')) { | |
pool.push(g.value); | |
} | |
Promise.all(pool); | |
} | |
spawn1(gen('spawn1')); | |
spawn2(gen('spawn2')); | |
asyncFunc('asyncFunc'); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
对 http://www.ruanyifeng.com/blog/2015/05/async.html 的回复:
对此并不十分赞同。async/await 并不是生成器函数和 yield 的替代,而是它们与某种特定的执行器加在一起的替代。而生成器函数的执行器不同,运行效果是完全不一样的。比如星号函数配合用 es6-promise-pool 或者 Promise.all() 实现的执行器可以实现多个 yield 操作的并发执行,这与 async 函数中 await 要做的事情完全不同(await 恰恰就是要等待本次调用的运行结果出来后再进行下次调用,而不是让其与下次调用同时发生)。
比如上面那个例子,输出是这样的:
可以看出,spawn2 的两个 sleep 是同一时间开始执行的,但是 spawn1 和 asyncFunc 的第二个 sleep 是等到第一个 sleep 执行完成后才开始执行的。
所以在这个例子中,async/await 并不等价于生成器函数 gen,而是等价于生成器函数 gen 和 spawn1 这个特定执行器的结合。