我正在尝试创建一个将多个函数作为参数并按顺序执行这些函数的函数,但每个函数都有并行执行函数的setTimeout
。是否可以使其顺序化?
var fun1=function(){
console.log('Started fun1');
setTimeout(()=>{console.log('Finished fun1');},2000)
}
var fun2=function(){
console.log('Started fun2');
setTimeout(()=>{console.log('Finished fun2');},2000)
}
function fun3(arr){
for(var i=0;i<arr.length;i++)
arr[i]();
}
fun3([fun1,fun2]);
您的函数是异步的,异步函数需要某种方法来指示它们何时完成。通常,这是通过回调或承诺来完成的。没有它,就没有办法知道它们何时完成。如果他们返回了承诺,您可以执行以下操作:
var fun1 = function() {
console.log('Started fun1');
return new Promise(resolve => {
setTimeout(() => {
console.log('Finished fun1');
resolve(true)
}, 2000)
})
}
var fun2 = function() {
console.log('Started fun2');
return new Promise(resolve => {
setTimeout(() => {
console.log('Finished fun2');
resolve(true)
}, 2000)
})
}
function fun3(arr) {
let p = Promise.resolve()
for (var i = 0; i < arr.length; i++){
p = p.then(arr[i]);
}
return p
}
fun3([fun1, fun2]);
您可以使用reduce()
更简洁地编写循环:
function fun3(arr){
return arr.reduce((a, c) => a.then(c), Promise.resolve())
}
如果你可以使用async/await
最后一个函数会更容易阅读。由于async
函数返回一个 promise,因此您还可以轻松知道整个事情何时完成:
async function fun3(arr){
for(var i=0;i<arr.length;i++)
await arr[i]();
}
fun3([fun1,fun2])
.then(() => console.log("finished"))
当然,如果可能只拥有非异步的简单函数,那么很多这些问题都会消失......您可以在函数之外的计时器中运行。
您可以在setTimeout
回调中添加下一个函数。
例如
var fun1=function(){
console.log('Started fun1');
setTimeout(()=>{
console.log('Finished fun1');
fun2(); // Start the next timeout.
},2000)
}
var fun2=function(){
console.log('Started fun2');
setTimeout(()=>{
console.log('Finished fun2');
},2000)
}
// This should output 'Started fun1', delay,
// output 'Finished fun1' and then 'Started fun2',
// delay, and then finally output 'Finished fun2'.
fun1();