これはsetInterval
すぐに本当に悪いIDEA ™になることができる場所です。
問題はこれです:
setInterval(lots_O_functions, 15);
何が起こるかを呼び出すとlots_O_functions
、15ミリ秒後に呼び出されますが、たとえば、すべての作業を完了するのに45ミリ秒かかる場合は、中断されることはなく、代わりにさらに2つのlots_O_functions
呼び出しが待機します。あなたの最初のものが終わったらすぐに実行するために...
...これらの2つも1つあたり45ミリ秒かかると仮定すると、さらに6つのlots_O_functions
呼び出しが並んで待機しています...
それはあなたがしたいことですか?知らない。個人的には、ほとんどの場合そうではないと思いますが、その理由は次のとおりです。
JSはシングルスレッドで実行されます。実際、VASTのほとんどの場合、ブラウザー内のほとんどすべて(クリック、ページ上の要素の再描画、ページを離れて別の場所に移動することさえ)はすべて同じスレッドに関連付けられています。
そのため、重い関数への呼び出しが重複してスレッドが詰まるのは良くありません™
代わりに、次のようなものを用意してみませんか。
var big_state_machine = { /*...*/ },
lots_O_work = function () {
big_state_machine.currentState.jobs.forEach(/*...*/);
/*....... do lots o' work ......*/
var more_work_to_do = /* figure out if you need to rerun lots_O_work */;
if (more_work_to_do) { setTimeout(lots_O_work, 20); }
};
lots_O_work();
これで、必要な処理を実行します。その後、さらに実行する必要がある場合は、setTimeoutを呼び出して、その時点から少なくとも20ミリ秒後に自分自身をキューに入れます。
setTimeout
sleep
aやaのようなものではなく、wait
「20ミリ秒先を見て、すでに何人の人が何かをするのを待っているかを確認してください... ...そこから始めて、次の利用可能な場所に私を並べてください」と書かれています。
ここでの違いは、最初の関数が終了してから20ミリ秒後に実行されることです。つまり、他の処理(クリック、ペイント、AJAXなど)が発生するまでに少なくとも20ミリ秒かかります。
を使用setInterval
すると、のようになりますが、事後setTimeout
に次の利用可能な場所にキューイングする代わりに、準備ができている(または必要な)かどうかに関係なく、キューに入れられます。
これをさらに分割して、応答性を維持することもできますが、これは良いスタートです。