JavaScriptでプログラムを実行する際に、特定の処理の実行を遅らせたい時があると思います。
その際に活用できるのが、setTimeoutメソッドです。
setTimeoutメソッドは、ページ表示などの特定のタイミングから一定時間後に処理を実行したりなど、タイマー機能としても活用できるメソッドとなっています。
今回はこの、setTimeoutメソッドの使用方法について、解説していきたいと思います。
基本的な方法から応用例まで詳しく解説していくので、ぜひ参考にしてみてください。
setTimeoutとは?
setTimeoutメソッドは、特定の処理の実行タイミングを遅らせたい場合に使用するメソッドです。
通常、コードは上から下へと記述順に実行されますが、setTimeoutメソッドを使用することにより、特定の処理の実行タイミングを指定した秒数だけ遅らせることができます。
また、上記の特徴から、Promise や async/await などの非同期処理と合わせて活用されることもあります。
setTimeoutの使い方
それでは早速、setTimeoutメソッドの使い方について見ていきましょう。
まずは、基本的な使い方から解説していきます。
基本構文
setTimeoutメソッドを使用する際の基本構文は、以下のように記述します。
【基本構文】
setTimeout(コールバック関数, 実行タイミング)第1引数には、遅延実行する処理内容を定義したコールバック関数を指定します。
(コールバック関数とは、関数内で実行するために渡される関数のことを言います)
第2引数には、処理を実行するタイミングをミリ秒 (1/1000 秒)単位で指定します。
例えば、該当処理の実行タイミングを1秒遅延させたい場合は、「1000」 と記述します。
以下のサンプルコードで、実際の記述例を見てみましょう。
【サンプルコード】
setTimeout(function() {
console.log("3秒経過しました");
}, 3000);上記の例の場合、実行開始から約3秒後にコンソールに文字列が出力されます。
ただし、指定した秒数は厳密に守られるものではなく、あくまで目安であることに注意が必要です。
setTimeoutメソッドは、指定した秒数が経過した際に対象の処理をすぐに実行するわけではなく、一旦タスクキューへと追加します。
タスクキューとは、実行待ちの関数を一時的に貯めておくための場所で、追加された関数は、既に呼び出し済みの関数(タスク)が完了するまで処理の実行が保留されます。
上述の仕様により、既存タスクの処理に時間がかかった場合に、タスクキューに追加した処理の実行が指定の秒数よりも遅れることがあります。
setTimeoutメソッドは、あくまでコードの実行順を大まかに調整するためのものであり、特定のタイミングで必ず処理を実行させるための関数ではない点に注意してください。
setTimeoutの活用例
setTimeoutメソッドを活用する方法は様々ですが、まずは簡単な例として、指定した秒数が経過した後にアラートを表示するサンプルコードを紹介します。
特定のイベントからn秒後にアラートを表示する
例えば、ページの読み込み完了時やボタンクリック時など、特定の処理やイベントをきっかけに setTimeoutメソッドを使用し、n秒後にアラートを表示する方法があります。
表示方法は単純で、以下のようなコードを対応する箇所に記述するだけです。
【サンプルコード】
setTimeout(function(){
alert(time + "3秒経過");
}, 3000);試しに、入力した秒数で設定する簡単なタイマーを実装してみましょう。
まずは、設定する秒数を入力するためのテキスト欄と、タイマーをセットするためのボタンをHTMLで配置します。
【サンプルコード】
<body>
<label>タイマー:<input type="text" id="telText"> 秒</label>
<input type="button" value="set" id="checkBtn">
</body>完了すると、以下のような画面が表示されるようになります。
続いて、setボタンを押した際にアラートがセットされるよう、コードを記述していきましょう。
JavaScriptで、以下のように処理を実装します。
【サンプルコード】
const text = document.getElementById('telText');
const checkBtn = document.getElementById('checkBtn');
checkBtn.addEventListener('click', () => {
const time = text.value;
setTimeout(function(){
alert(time + "秒経過");
}, time * 1000);
});入力した秒数で無事にアラートが表示されれば、成功です。
clearTimeoutでタイマーを停止する
セットした処理を中断させたいケースも中にはあるかと思います。
その場合は、clearTimeoutメソッドを使用しましょう。
clearTimeoutメソッドの引数には、中断させたい setTimeoutメソッドの識別子(ID) を指定する必要があります。
IDは、setTimeoutメソッドの戻り値で取得することができます。
【サンプルコード】
const id = setTimeout(function(){
console.log("3秒経過");
}, 3000);
clearTimeout(id);setTimeoutの応用例
ここからは、setTimeoutメソッドの応用的な使い方や、使用時に注意するべきいくつかの点について紹介していきたいと思います。
それぞれ、順に確認していきましょう。
複数のタイマー処理を実行する
非同期に処理したい複数の関数を、任意の順番で実行されるようにしたいケースもあると思います。
簡単な実装方法としては、コールバック関数の中で再度 setTimeoutメソッドを呼び出す方法があります。
【サンプルコード】
setTimeout(function() {
console.log(“3秒経過しました");
setTimeout(function() {
console.log(“1秒経過しました");
}, 1000);
}, 3000);ただし、この方法はコールバック地獄と呼ばれる状態に陥りやすく、コードの可読性が下がる可能性が高いためお勧めできません。
上記のような処理を実装したい場合は、Promise.thenメソッド や async/await と組み合わせて使用しましょう。
【サンプルコード】
const timer = function(time) {
return new Promise(function (resolve) {
setTimeout(function() {
console.log(time + "秒経過");
resolve();
}, time * 1000);
});
};
// Promise.then()の場合
timer(3)
.then(function() {
timer(1)
})
.then(function() {
timer(2)
});
// async/awaitの場合
async function sampleFunc() {
await timer(3);
await timer(1);
await timer(2);
}先ほども解説したように、setTimeoutメソッドの第1引数に指定するのはコールバック関数です。
この際に気を付けるべきポイントとして、渡すのはあくまで関数そのものであることに注意する必要があります。
まずは、以下の例を見てみましょう。
【サンプルコード】
const sampleFunc = function() {
console.log("関数を実行しました");
}
setTimeout(sampleFunc(), 3000);このサンプルコードを実行すると、次のようなエラーが発生します。
TypeError [ERR_INVALID_CALLBACK]: Callback must be a function. Received undefinedエラーが発生する原因は、関数名の後ろに () が記述されていることによって、関数そのものではなく実行結果を引数に渡してしまっているからです。
このように、関数の記述の仕方によっては、正しく引数に渡せない場合があるので注意してください。
setTimeoutに0ミリ秒を渡したときの動作
setTimeoutメソッドは、第2引数に指定した秒数分だけ処理を遅延させます。
では、0ミリ秒を指定した場合の挙動はどのようなものになるのでしょうか?
まずは、以下の例を実行してみましょう。
【サンプルコード】
setTimeout(function() {
console.log("関数を実行しました");
}, 0);
console.log("Hello World!");【実行結果】
Hello World!
関数を実行しました結果を見てみると、setTimeoutメソッドより後に記述したコードが先に実行されているのが分かりますね。
既に上述したように、setTimeoutは指定の時間に即座に処理を実行するメソッドではなく、一旦退避させた処理をタスクキューへと追加するメソッドです。
そのため、タスクキューへの追加時点で既に呼び出されていた console.logメソッドが先に実行され、その後に追加した処理が実行されています。
このような使い方をするケースは稀ですが、0ミリ秒を指定しても即時実行されるわけではない点には注意しておきましょう。
コールバック関数や引数を活用する
コールバック関数自身に引数を渡す方法や、thisキーワードを使用する際の挙動にも、いくつか気を付けるべき点があります。
それぞれの使用方法について見ていきましょう。
コールバック関数に引数を渡す
setTimeoutメソッドで実行する関数に引数を渡したい場合は、メソッドの第3引数以降に値を指定します。
【サンプルコード】
function sampleFunc(name) {
console.log(name);
}
setTimeout(sampleFunc, 3000, "Taro Yamada");【実行結果】
Taro Yamada関数に値を直接渡してしまうと、実行結果をメソッドの引数に渡したと見なされ、エラーが発生するので注意が必要です。
【エラーになるサンプルコード】
function sampleFunc(name) {
console.log(name);
}
// 引数を正しく渡さなかったとされてエラーが発生する
setTimeout(sampleFunc("Taro Yamada"), 3000);thisを使用して関数自身を指定する
thisキーワードは、グローバルオブジェクト(Windowなど)、もしくはメソッドの呼び出し元となるオブジェクト自身を参照するキーワードです。
主にクラス内のプロパティを参照する時などに使用されますが、呼び出し方による参照先の違いを正しく理解していないと、想定外の動作を引き起こす原因となる場合があります。
まずは、以下の例を見てみましょう。
【サンプルコード】
class sampleClass {
constructor() {
this.text = "成功しました";
}
showLog() {
console.log(this.text);
}
}
const sample = new sampleClass();
setTimeout(sample.showLog, 1000);【実行結果】
undefined上記のサンプルコードは、thisキーワードによる参照が上手くいかない失敗例の1つです。
sampleClassの textプロパティの値をコンソールに表示しようとしましたが、結果は undefinedとなっています。
通常、メソッド内における thisキーワードは生成したインスタンス自身を参照しますが、setTimeoutメソッドのコールバック関数として実行すると、参照先がグローバルオブジェクトになってしまうのです。
そのため、指定したプロパティが存在せず、undefinedが表示されてしまいます。
この場合の解決策は以下のように、新たに定義した関数内でメソッドを実行する方法があります。
【サンプルコード】
setTimeout(function() {
sample.showLog();
} , 1000);【実行結果】
成功しましたsetTimeoutのコールバック関数内で thisキーワードを使用する際は、参照先に注意するようにしてください。
setTimeoutとsetIntervalの違い
JavaScriptには、setTimeoutに似たメソッドに、setIntervalというメソッドがあります。
setTimeoutメソッドは、対象の処理を指定の時間分だけ遅延させるメソッドです。
一方、setIntervalメソッドは、指定の時間が経過するごとに対象の処理を繰り返すメソッドとなっています。
setTimeoutの場合、指定の処理が実行されるのは一度だけですが、setIntervalの場合はメソッドが停止されるまで処理が永続的に繰り返され続けます。
そのため、停止用のメソッドである clearIntervalと合わせて使用する必要があります。
【サンプルコード】
let count = 0;
const id = setInterval(function() {
count += 1;
console.log(count);
}, 1000);
setTimeout(function() {
clearInterval(id);
}, 6000);【実行結果】
1
2
3
4
5メソッドを使い分ける際は、該当の処理を繰り返し実行する必要があるかどうかで判断するといいでしょう。
まとめ
いかがでしたか?今回は、JavaScriptで setTimeoutメソッドを使用する方法について解説しました。
JavaScriptには、他の言語で実装されているような sleep機能が存在しないため、よくこの setTimeoutメソッドを応用して実装されたりします。
その他にも、様々なケースで活用されるメソッドですので、ぜひこの機会に使い方を覚えて、実際の開発にも役立ててみてください。
JavaScriptの勉強方法は?
書籍やインターネットで学習する方法があります。昨今では、YouTubeなどの動画サイトやエンジニアのコミュニティサイトなども充実していて多くの情報が手に入ります。
そして、より効率的に知識・スキルを習得するには、知識をつけながら実際に手を動かしてみるなど、インプットとアウトプットを繰り返していくことが重要です。特に独学の場合は、有識者に質問ができたりフィードバックをもらえるような環境があると、理解度が深まるでしょう。
ただ、JavaScriptに限らず、ITスキルを身につける際、どうしても課題にぶつかってしまうことはありますよね。特に独学だと、わからない部分をプロに質問できる機会を確保しにくく、モチベーションが続きにくいという側面があります。独学でモチベーションを維持する自信がない人にはプログラミングスクールという手もあります。費用は掛かりますが、その分スキルを身につけやすいです。しっかりと知識・スキルを習得して実践に活かしたいという人はプログラミングスクールがおすすめです。
プログラミングスクールならテックマニアがおすすめ!
ITスキル需要の高まりとともにプログラミングスクールも増えました。しかし、どのスクールに通うべきか迷ってしまう人もいるでしょう。そんな方にはテックマニアをおすすめします!これまで多くのITエンジニアを育成・輩出してきたテックマニアでもプログラミングスクールを開講しています。
<テックマニアの特徴>
・たしかな育成実績と親身な教育 ~セカンドキャリアを全力支援~
・講師が現役エンジニア ~“本当”の開発ノウハウを直に学べる~
・専属講師が学習を徹底サポート ~「わからない」を徹底解決~
・実務ベースでスキルを習得 ~実践的な凝縮カリキュラム~
このような特徴を持つテックマニアはITエンジニアのスタートラインとして最適です。
話を聞きたい・詳しく知りたいという方はこちらからお気軽にお問い合わせください。