Javascript - 使用生成器而不是promises

时间:2016-03-08 16:21:35

标签: javascript promise generator co

假设我有以下功能:

var f1 = function() {
    console.log('running f1');
    return new Promise(function(res, rej) {
        setTimeout(() => res('resolved_1!'), 1000);
    });
};

var f2 = function(a) {
    console.log('running f2 with ' + a);
    return new Promise(function(res, rej) {
        setTimeout(() => res('resolved_2!'), 2000);
    });
};

var f3 = function() {
    console.log('running f3');
    return new Promise(function(res, rej) {
        setTimeout(() => res('resolved_3!'), 3000);
    });
};

我可以用:

运行它们
let t1 = +new Date;
Promise.all([
    f1().then(a => {
        return f2(a);
    }),
    f3()
]).then((result) => {
    let t2 = +new Date;
    console.log(t2 - t1);
});

大约需要3秒钟。

现在我想使用生成器来运行这些函数:

let t1 = +new Date;
let result = yield [f1(), f3()];
yield f2(result[0]);
let t2 = +new Date;
console.log(t2 - t1)

由于我需要解析f1的值来调用f2,我将等待f1完成。这需要5秒钟。我怎样才能获得相同的3秒但使用发电机?

1 个答案:

答案 0 :(得分:1)

  

这需要5秒钟。

请参阅Slowdown due to non-parallel awaiting of promises in async generators

  

如何使用发电机获得相同的3秒钟?

您只需要表达相同的控制流程:

let t1 = +new Date;
let result = yield [f1().then(f2), f3()];
let t2 = +new Date;
console.log(t2 - t1)

如果您出于某种原因想避免使用then,而是使用生成器,则必须

let t1 = +new Date;
let result = yield [co(function*() {
    var a = yield f1();
    return yield f2(a); // yield is optional here
}), f3()];
let t2 = +new Date;
console.log(t2 - t1)