Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/jquery/77.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript 如何按顺序或同步执行函数_Javascript_Jquery_Html_Promise - Fatal编程技术网

Javascript 如何按顺序或同步执行函数

Javascript 如何按顺序或同步执行函数,javascript,jquery,html,promise,Javascript,Jquery,Html,Promise,我有4个函数,我想按顺序执行 尤其是第四个功能仅应在前三个功能全部完成时执行 我尝试使用回拨,但肯定没有正确使用。我如何使它连续 我听说过JavaScript中的然后函数,但它似乎只适用于ECMAScript 6(不确定),但当我尝试在脚本中使用它时,会出现一个未定义的错误 函数longRunningFunction(回调){ setTimeout(函数(){ $('#div1').html('div1 Done'); }, 5000); setTimeout(函数(){ $('#div2')

我有4个函数,我想按顺序执行

尤其是第四个功能仅应在前三个功能全部完成时执行

我尝试使用回拨,但肯定没有正确使用。我如何使它连续

我听说过JavaScript中的
然后
函数,但它似乎只适用于
ECMAScript 6
(不确定),但当我尝试在脚本中使用它时,会出现一个未定义的错误

函数longRunningFunction(回调){
setTimeout(函数(){
$('#div1').html('div1 Done');
}, 5000);
setTimeout(函数(){
$('#div2').html('div2 Done');
}, 5000);
setTimeout(函数(){
$('#div3').html('div3 Done');
}, 5000);
回调();
}
longRunningFunction(函数(){
setTimeout(函数(){
$('#div4').html('butchanges1st!');
}, 3000);
});
#第4部分{
字体大小:粗体;
颜色:红色;
}
#第一组{
边缘顶部:20px;
}

我的内容应该是最后的改变!
第一组
第二组
第三组

您可以使用
承诺来实现这一点。
为将要发生的每个异步更改设置承诺,并等待它们完成:

演示:

函数longRunningFunction(回调){
让p1=新承诺((解决、拒绝)=>{
setTimeout(函数(){
$('#div1').html('div1 Done');
解决();
}, 5000);
});
让p2=新承诺((解决、拒绝)=>{
setTimeout(函数(){
$('#div2').html('div2 Done');
解决();
}, 5000);
});
让p3=新承诺((解决、拒绝)=>{
setTimeout(函数(){
$('#div3').html('div3 Done');
解决();
}, 5000);
});
承诺。所有([p1,p2,p3])。然后(()=>{
回调();
});
}
longRunningFunction(函数(){
$('#div4').html('butchanges1st!');
});
#第4部分{
字体大小:粗体;
颜色:红色;
}
#第一组{
边缘顶部:20px;
}

我的内容应该是最后的改变!
第一组
第二组
第三组

您可以试试发电机

函数*generateSequence(){
产量1;
产量2;
返回3;
}
让生成器=generateSequence();
设one=generator.next();

警报(JSON.stringify(一));//{value:1,done:false}
您有关于setTimeout的x4函数,因此您可以将简单函数与promise和异步/等待功能结合起来:

只需将console.log()替换为
()=>$('div1').html('div1 Done')

函数顺序超时(时间,func){
返回新承诺(resolve=>setTimeout(()=>resolve(func()),time));
}
异步函数序列(){
等待顺序超时(500,()=>console.log('1'))
等待顺序超时(500,()=>console.log('2'))
等待顺序超时(500,()=>console.log('3'))
顺序超时(500,()=>console.log('4'))
}

sequence()
正如另一个答案所说,您可以使用承诺。但是,如果您认为对于这样一个简单的用例(可以说是这样),这太“繁重的机器”了,那么您可以为每个成功的超时设置一个标志,然后在设置完所有超时后启动回调。以下是一种方法:

function longRunningFunction(callBack) {

  var done = [false, false, false];

  function checkIfDone(cb) {
    if (done[0] && done[1] && done[2]) {
      cb();
    }
  }

  setTimeout(function() {
    $('#div1').html('Div1 Done');
    done[0] = true;
    checkIfDone(callBack);
  }, 5000);
  setTimeout(function() {
    $('#div2').html('Div2 Done');
    done[1] = true;
    checkIfDone(callBack);
  }, 5000);
  setTimeout(function() {
    $('#div3').html('Div3 Done');
    done[2] = true;
    checkIfDone(callBack);
  }, 5000);
}
longRunningFunction(function() {
  setTimeout(function() {
    $('#div4').html('But changes 1st!');
  }, 3000);
});

是否希望
Div2 Done
发生在
Div1 Done
之后5000ms?将
callback()
放在最后一次
setTimeout()的末尾。我还建议使用队列而不是超时,因为它提供了更多可扩展的控制。@CertainPerformance,否。我只希望在所有3个函数完成后进行回调。您在尝试
然后
时遇到了什么错误?承诺是您的场景的最佳解决方案,因此最好弄清楚您是否错误地使用了承诺,而不是想出一个不太可靠的替代方案。@Simsons承诺在所有当代浏览器中都是本机支持的。但它们并不是神奇的,你需要显式地创建一个承诺(或调用一个这样做的函数)来使用它的
.then()
方法。超时只是OP用来更好地确保所有3个在第4个之前完成的延迟。所以你可以删除答案中的那些。我们应该调用longRunningFunction而不是回调函数吗?第4部分没有改变@西蒙斯,我在
Promise#all
通话中打错了。现在已修复。不要传递回调。如果您确实需要,只需使用
,然后使用
。您的方法在捕获
func()
调用中的错误时也失败。@Bergi我认为1深度回调是一种很好的方法。为什么你的想法正好相反?2.为了简单起见,我没有添加拒绝。如果您使用的是
wait
,则根本不需要回调;如果你想使用它,那么它应该是一个promise
then
callback。不,您不仅仅错过了一个
拒绝
(您会在哪里这样做,为什么在超时后?),您没有从
func
捕获异常。然后使用
将自动完成这项工作。生成器(单独)无助于使异步代码顺序化。
function longRunningFunction(callBack) {

  var done = [false, false, false];

  function checkIfDone(cb) {
    if (done[0] && done[1] && done[2]) {
      cb();
    }
  }

  setTimeout(function() {
    $('#div1').html('Div1 Done');
    done[0] = true;
    checkIfDone(callBack);
  }, 5000);
  setTimeout(function() {
    $('#div2').html('Div2 Done');
    done[1] = true;
    checkIfDone(callBack);
  }, 5000);
  setTimeout(function() {
    $('#div3').html('Div3 Done');
    done[2] = true;
    checkIfDone(callBack);
  }, 5000);
}
longRunningFunction(function() {
  setTimeout(function() {
    $('#div4').html('But changes 1st!');
  }, 3000);
});