2016-11-04 18 views
0

setIntervalで問題が発生しました& clearInterval。
私のコードでは、複数の間隔を設定し、カウントが0になると実行を停止します。以下のようにJavascript - clearIntervalが複数のsetIntervalのときに機能しない

:、それはまだ行く:コンソール後

<!DOCTYPE html> 
<html> 
    <head> 
     <meta name="viewport" content="initial-scale=1.0" charset="utf-8"> 
    </head> 
    <body> 
    <body> 
     <script type="text/javascript"> 
      for (var i=0; i<4; i++){ 
       var count = 100; 

       var IntervalID = window.setInterval((function(){ // closure 
        var timeoutID = IntervalID; // temp 
        var countTemp = count; // temp 
        var id = i; 

        return function(){ 
         countTemp --; 
         console.log(id + " " + countTemp); 

         // do something here 

         if (countTemp == 0){         
          clearInterval(timeoutID); // stop the execution 
          console.log(id + " stop"); 
         } 
        } 
       })(), 20); 
      } 
     </script> 
    </body> 
</html> 

は停止メッセージ "Xストップ"、最後の要素(3 ID)を除くすべての要素の停止を表示されます。

私は別の形で私のコードを書いてみる:

<!DOCTYPE html> 
<html> 
    <head> 
     <meta name="viewport" content="initial-scale=1.0" charset="utf-8"> 
    </head> 
    <body> 
     <script type="text/javascript"> 
      for (var i=0; i<4; i++){ 
       doSomething(i); 
      } 

      function doSomething(id){ 
       var count = 100; 

       var IntervalID = window.setInterval((function(){ // closure 
        var timeoutID = IntervalID; // temp 
        var countTemp = count; // temp 

        return function(){ 
         countTemp --; 
         console.log(id + " " + countTemp); 

         // do something here 

         if (countTemp == 0){         
          clearInterval(timeoutID); // stop the execution 
          console.log(id + " stop"); 
         } 
        } 
       })(), 20); 
      } 
     </script> 
    </body> 
</html> 

しかし、今回、全ての要素が停止しないでください。

私は2つの質問があります:
1.これら2つのコードの違いは何ですか?
2.コードを正常に動作させるにはどうすればよいですか?

編集:

clearInterval(timeoutID); // stop the execution 

clearInterval(IntervalID); // stop the execution 

にでも他の人の答えは解決することができます:あなただけのコードを仕事にしたい場合は
、唯一の第二のスニペットの1行を変更この問題で私が混乱するもの

+0

値を達成するためにループを変更した、オブジェクトと一緒に使用することができますあなたはそれを使用しようとしていますか? Console.logは、varのすぐ下の1つです。timeoutID = IntervalID; – Mati

+3

最初のスニペットでは、setIntervalの呼び出しがまだ完了していないため、 'timeoutID'は' i == 0'のために未定義です。したがって、 'console.log(i +" - "+ IntervalID);を' var timeoutID = IntervalID;の直前に追加します。 // tempはあなたに '0 - 未定義'、次に '1 - 1'、' 2 - 2'、 '3 - 3'を表示します – enhzflep

+0

ああ、最初のスニペットで、' countTemp'が0、 'clearInterval(timeoutID);'実際に前のものを停止する( 'id == 1 'セクションで' id == 0 'を実行しない;' id == 2 'stop' id == 1';など) id == 3を止める人はいないので、それはまだ進行中です)。 – CryMasK

答えて

0

問題は、正確なIntervalIDが閉包でキャプチャされていないことです。閉包が実行されるまでに、割当て式がまだ完了していないため、window.setIntervalはidを返していません。

彼らはJavaScript

参照により関数に渡されるので、簡単なトリックは、私があるこの-S INTERVALIDは何

for (var i=0; i < 4; i++){ 

    var count = 100; 

    var args = { id: i, counter: count }; 
    var IntervalID = window.setInterval((function(args){ // closure 

     return function(){ 
      args.counter--; 
      console.log(args.id + " " + args.counter) 
      if (args.counter == 0){         
       clearInterval(args.IntervalID); // stop the execution 
       console.log(args.id + " stop"); 
      } 
     }.bind(args); 
    })(args), 20); 

    // by now the correct IntervalID will be captured 
    // as the assignment expression has finished executing 
    args.IntervalID = IntervalID; 
} 
+0

ありがとう、今私はより明確に理解する。 私自身の質問に答えてください1、最初のスニペットでは、 'timeoutID'はメモリに残っている前の' IntervalID'を捕捉します。最後のものだけを止めることはできません。 2つ目のスニペットでは、関数が終了した後にfounctionスタックから1つの関数とpopを呼び出すので、 'timeoutID'は値を取り込めず、' undefined'ですべての要素/ intervalIsを停止できません。 – CryMasK

関連する問題