代码之家  ›  专栏  ›  技术社区  ›  KingKongFrog

Javascript闭包setTimeout间隔问题

  •  2
  • KingKongFrog  · 技术社区  · 10 年前

    为什么每1秒记录一次以下内容?我将1000毫秒乘以增量。我的日志不应该在1秒、2秒、3秒后显示吗?

    for (var i = 0; i < 5; i++) {
      (function(r) {
        setTimeout(
          function() { 
            console.log(r)
          } 
        , r * 1000 );
      })(i)
    }
    

    JSFIDDLE

    4 回复  |  直到 10 年前
        1
  •  4
  •   user3276552    10 年前

    它工作正常,基本上,循环是编写以下内容的速记:

    setTimeout( function(){ console.log(0) }, 1000)
    setTimeout( function(){ console.log(1) }, 2000)
    setTimeout( function(){ console.log(2) }, 3000)
    setTimeout( function(){ console.log(3) }, 4000)
    setTimeout( function(){ console.log(4) }, 5000)
    

    所以每个人都会一个接一个地离开,看起来像这样:

    ▀
    ▀▀
    ▀▀▀
    ▀▀▀▀
    ▀▀▀▀▀
    

    你可能想要的是

    (function newTimeout( seconds ){
      if( seconds > 4 ) return;
      console.log(seconds);
      setTimeout( function(){
        newTimeout( seconds + 1 )
      }, seconds * 1000);
    })(0);
    

    看起来像这样

    ▀
     ▀▀
       ▀▀▀
          ▀▀▀▀
              ▀▀▀▀▀
    

    希望它有帮助!

        2
  •  3
  •   Allan Chua    10 年前

    实际上,你的循环兄弟没有什么问题。发生的情况是setTimeout同时执行。记住,小循环的执行时间仅为几毫秒。

    概念证明。

            for (var i = 0; i < 5; i++) {
                console.log(new Date() + " Loop Executed: " + (i + 1));
                (function (r) {
                    setTimeout(
                      function () {
                          console.log(new Date() + " " + r)
                      }
                    , (r * 1000));
                })(i)
            }
    
        3
  •  2
  •   Jaromanda X    10 年前

    为什么每1秒记录一次以下内容?

    因为第一个记录在0 x 1000ms后,第二个记录在1 x 1000ms之后,第三个记录在2 x 1000ms…所以,在0、1、2、3、4秒之后

    我的日志不应该在1秒、2秒、3秒后显示吗?

    实际上,在0、1、2、3和4秒后-但这不是累积的,您实际上是在同一时间开始所有超时

        4
  •  2
  •   Spencer Wieczorek    10 年前

    那是因为打电话 setTimeout 不会停止代码的执行。循环将继续,并执行所有 setTimeout() 从一开始就在每个循环中。这就是它每秒记录的原因。它们确实会在1、2、3和4秒后熄灭,但同时启动。