我想覆盖async.waterfall()
(或写timed_waterfall()
),以便打印每一步的执行时间。怎么做?
async.waterfall([
f=>{
console.log('step1');
f();
},
f=>{
console.log('step2');
f();
},
f=>{
console.log('step3');
f();
},
],
()=>{
console.log('done');
})
期望的输出:
step1
1ms
step2
2ms
step3
1ms
done
5ms
答案 0 :(得分:1)
与 async.js waterfall()
兼容:
function timed_waterfall(tasks, ender) {
function color(a) {
if (a == undefined) { return '\u001b(B\u001b[m' }
return '\u001b[38;5;'+a+'m'
}
var N = 0;
function go(args) {
function f() {
if (N>0)console.timeEnd(color(1)+' * '+N+color())
var res = Array.prototype.slice.apply(arguments);
if (res[0]) {
ender.apply(null, res);
}
else {
res.splice(0, 1);
var cb = tasks.shift();
if (cb) {
res.push(f);
console.time(color(1)+' * '+(++N)+color())
cb.apply(null, res);
}
else {
res.unshift(null)
ender.apply(null, res);
}
}
}
f(null);
}
go([]);
}
很容易修改以打印总数。
答案 1 :(得分:1)
这个怎么样?
function timedWaterfall (tasks, callback) {
console.time('total')
async.waterfall(tasks.map(function (task, i) {
return function () {
if (i > 0)
console.timeEnd('step' + i)
console.time('step' + (i + 1))
return task.apply(null, arguments)
}
}),
function () {
console.timeEnd('total')
callback.apply(null, arguments)
})
}

答案 2 :(得分:1)
您根本不需要修改waterfall
- 只需编写一个包装函数,为任务添加时间(回调函数):
function withTiming(fn, name) {
if (typeof name == "number") name = "step"+name;
return function() {
var start = Date.now()
var lastIndex = arguments.length-1;
var cb = arguments[lastIndex];
arguments[lastIndex] = function() {
console.log(name+": "+(start-Date.now())+"ms");
cb.apply(this, arguments);
};
return fn.apply(this, arguments);
};
}
你可以像这样使用async.js:
async.waterfall([
f=>{
console.log('step1');
f();
},
f=>{
console.log('step2');
f();
},
f=>{
console.log('step3');
f();
},
].map(withTiming), ()=>{
//^^^^^^^^^^^^^^^
console.log('done');
})