JavaScript,等待值改变循环

时间:2017-06-29 14:31:31

标签: javascript

我正在尝试等待加载API,但是我的测试代码似乎没有将超时延迟考虑在内,因为它的循环过快。

var google = false;
  function test(check = false) {
    if (!check) {
      console.log('append the api');

      check = true;
    }
    if (check) {
      console.log('check api is loaded');
      if(!google){
        console.log('not loaded');
        setTimeout(test(true), 10000);
        return;
      } else {
        console.log('loaded');
      }
    }
  }

此代码应该只显示2个console.log,直到google变量更改为true。

我无法改变这一点,因为浏览器因为这么多循环而冻结了。

3 个答案:

答案 0 :(得分:2)

你的错在这一行:

setTimeout(test(true), 10000);

您必须传递该功能并且不要调用它。如果要传递参数,请执行以下操作:

setTimeout(function(){test(true)}, 10000);

答案 1 :(得分:2)

正如 Jonas w 所说,您应该使用setTimeout(test,1000,true)代替setTimeout(test(true),1000),请参阅以下说明:

根据MDN WindowOrWorkerGlobalScope.setTimeout(),您应该将三个变量传递给setTimeoutfunctiontimeout valueparameters,这些变量将传递给调用函数。 JavaScript中的函数是first class objects,因此您将它们作为常规对象传递。在您的示例中,您实际上并未传递函数,而是立即调用它并将setTimeout传递给此函数返回的值。

答案 2 :(得分:0)

您正在以递归方式立即调用test函数,因为您实际上是为test返回的值设置了超时,这是未定义的。

您希望将test(true)放入匿名函数中,如下所示:

var google = false;
function test(check = false) {
  if (!check) {
    console.log('append the api');
    check = true;
  }
  if (check) {
    console.log('check api is loaded');
    if(!google){
      console.log('not loaded');
      setTimeout(() => test(true), 10000);
      return;
    } else {
      console.log('loaded');
    }
  }
}

注意箭头() => - 这会创建一个在超时时间后调用的匿名函数。如果你不喜欢使用这个新奇的箭头函数,你也可以写:

var google = false;
function test(check = false) {
  if (!check) {
    console.log('append the api');
    check = true;
  }
  if (check) {
    console.log('check api is loaded');
    if(!google){
      console.log('not loaded');
      setTimeout(function () {
        test(true);
      }, 10000);
      return;
    } else {
      console.log('loaded');
    }
  }
}