Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/435.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-递归setInterval调用父函数两次-为什么?_Javascript_Recursion_Memory Leaks_Setinterval - Fatal编程技术网

JavaScript-递归setInterval调用父函数两次-为什么?

JavaScript-递归setInterval调用父函数两次-为什么?,javascript,recursion,memory-leaks,setinterval,Javascript,Recursion,Memory Leaks,Setinterval,我在HTML5文档的头部有一段简单的代码: var lol = 0; function madeMyDay() { lol++; console.log(lol); setInterval(madeMyDay, 1000); } 首次从以下位置调用函数: <script> madeMyDay(); </script> 但我得到: 1 (at start) 2 (after 1 sec) 3 (after 2 sec) 4 (after 2 s

我在HTML5文档的头部有一段简单的代码:

var lol = 0;

function madeMyDay() {
  lol++;
  console.log(lol);
  setInterval(madeMyDay, 1000);
}
首次从以下位置调用函数:

<script>
  madeMyDay();
</script>
但我得到:

1  (at start)
2  (after 1 sec)
3  (after 2 sec)
4  (after 2 sec, together with 3)
5  (after 3 sec)
6  (after 3 sec, together with 5)
7  (after 3 sec, together with 5)
8  (after 3 sec, together with 5)
9  (after 4 sec)
10 (after 4 sec, together with 9)
11 (after 4 sec, together with 9)
12 (after 4 sec, together with 9)
13 (after 4 sec, together with 9)
14 (after 4 sec, together with 9)
15 (after 4 sec, together with 9)
16 (after 4 sec, together with 9)
...
这当然会使浏览器在几分钟甚至几十秒钟内由于内存泄漏而崩溃

看起来setInterval调用父函数两次-我不知道为什么以及如何防止这种奇怪的行为

我尝试了设置超时-它正确地完成了任务。我不明白setInterval的魔力是什么


PS.-在Kubuntu上的最新Chrome上进行了测试

您想使用setTimeout,因为它只调用函数一次

这允许您执行递归位以保持其运行

否则,setInterval会在间隔上重复函数调用,因此

setInterval(function () {console.log(Date.now()), 1000);
将每秒重复一次

编辑:为了向您展示setInterval的工作原理,这也是解决问题的有效方法:

var lol = 0;

setInterval(madeMyDay, 1000);

function madeMyDay() {
  lol++;
  console.log(lol);
}

注意这里没有递归。setInterval执行重复操作。

您想使用setTimeout,因为它只调用函数一次

这允许您执行递归位以保持其运行

否则,setInterval会在间隔上重复函数调用,因此

setInterval(function () {console.log(Date.now()), 1000);
将每秒重复一次

编辑:为了向您展示setInterval的工作原理,这也是解决问题的有效方法:

var lol = 0;

setInterval(madeMyDay, 1000);

function madeMyDay() {
  lol++;
  console.log(lol);
}

注意这里没有递归。setInterval执行重复操作。

将setInterval更改为setTimeout

function madeMyDay() {
  lol++;
  console.log(lol);
  setTimeout(madeMyDay, 1000);
}

将setInterval更改为setTimeout

function madeMyDay() {
  lol++;
  console.log(lol);
  setTimeout(madeMyDay, 1000);
}

您可以在设置间隔之前检查间隔是否已定义

var lol = 0;

function madeMyDay() {
  lol++;
  console.log(lol);
  if(typeof myInterval == "undefined") {
    var myInterval = setInterval(madeMyDay, 1000);
  }
}

您可以在设置间隔之前检查间隔是否已定义

var lol = 0;

function madeMyDay() {
  lol++;
  console.log(lol);
  if(typeof myInterval == "undefined") {
    var myInterval = setInterval(madeMyDay, 1000);
  }
}

对setInterval的一次调用会一直重复,直到你调用clearInterval为止。对setInterval的一次调用会一直重复,直到你调用clearInterval为止。哦,这就是神奇之处。。。所以我没有正确理解设置间隔,谢谢!正如你所看到的,两者都可以使用。在我看来,通过在setTimeout版本中有条件地中断递归来停止循环要比存储setInterval的结果并将其与clearInterval一起使用容易得多。是的,这就是我在回答之前所做的,但我仍然不知道setInterval一直在重复。。。谢谢你的澄清!没问题。如果你想的话,你也可以把它作为解决方案。哦,这就是魔法。。。所以我没有正确理解设置间隔,谢谢!正如你所看到的,两者都可以使用。在我看来,通过在setTimeout版本中有条件地中断递归来停止循环要比存储setInterval的结果并将其与clearInterval一起使用容易得多。是的,这就是我在回答之前所做的,但我仍然不知道setInterval一直在重复。。。谢谢你的澄清!没问题。如果需要,您也可以将其作为解决方案进行检查。