Web制作、Web開発の歩き方

JavaScriptのきほんを学ぼう

■第2話:【初学者向け】 var, let, constの使い分けと変数のスコープ、巻き上げ

(最終更新日:2022.05.24)

JavaScriptの猫
この記事は5分で読めます!
(絵が小さい場合はスマホを横に)

「変数宣言ってどれを使うの?」

ほんの少し昔までは、JavaScriptの変数宣言は全てvarだった。 しかし、IEがサポートを終了しEdgeに切り替わった昨今、varは無用の産物となった。 ちょっと前までvarで覚えた人、今からプログラミング学習をする人、是非ここでconstとletの使い方を押さえておこう。 そして結論だけ先に言うと、変数宣言は「極力const、駄目ならlet」を選択してほしい。


1. const, let, varの特徴

const, let, varの特徴をまとめると、下表のようになる。
主な違いとしては、「再定義(再宣言)できるか」「再代入できるか」「スコープはブロックか関数か」の三点になる。 巻き上げに関しても違いはあるのだが、これは違いというよりも、JavaScriptには巻き上げがあるということを憶えておこう。 varが良くないのは、再定義できてしまうこと、スコープが関数であることの2点である。この点がconstとletで改善されている。

const, let, varの特徴のまとめ

const, let, varの特徴のまとめ

2. 再定義ができることによるバグの例

varは再定義できてしまう。だから使わない方が良いと言われている。 実際どんなバグが生じることがあるのか、実例を通して確認してみよう。 下に示したHTMLとJavaScriptのコードは、 1と2のボタンを押したときに「自分自身の番号と繰り返し回数を言う」プログラムである。 また、3を押したときだけ「アホ」と言うプログラムにしている。 赤線部分の変数宣言をletで設定すると、1のボタンを押したときは「1:0(ボタンの番号:繰返回数)」、 2のボタンを押したときは「2:1」と言ってくれる。 そして、3のボタンを押したときは(i==2)が成立し「アホ」と言う。これが、正しく設定した通りの動きである。

しかし、赤下線部分のletをvarにしてしまうとどうなるだろうか。 答えは、どのボタンを押しても全て「アホ」と言う。 これは、varが関数スコープ(for文ではスコープが効かない)で再定義可能だからである。 つまり、i=2の時に定義した値で全て上書きしてしまっているのである。

「 再定義可能である危険性をご理解頂けただろうか?」

letだと正常に動き、varだと不具合が生じる例

letだと正常に動き、varだと不具合が生じる例

3. 再代入が必要な場合はletで書こう

次にconstとletの使い分けを考えよう。1の表にある通り、constとletの違いは再代入できるか否かである。 つまり、再代入する必要がある場合はlet、必要がない場合はconstを使う。

ここで、最もよく使う再代入の例を示そう。 プログラミングをしたことのある人なら、必ず一度は使ったことがあるはずだ。 そう。for文である。このインクリメントは通常letで宣言していた。 これをconstにすると、どうなるだろうか。 答えは簡単。再代入できないから、インクリメントできず「エラー」になるのである。

ちなみに、このletをvarに変え、for文の外でconsole.log(i)を実行すると何が表示されるだろうか。 「50」が表示されてしまうのである。(ちなみに、letの場合はiは定義されてないとエラーが出る) データがリセットされないというのは不具合の元なので、for文でもvarでなくletを使う癖をつけよう。

for文のインクリメントはletで

for文のインクリメントはletを使おう


4. JavaScriptが巻き上げを採用する理由

最後に、JavaScriptが巻き上げをする理由について簡単に述べる。 そこまで重要ではないので、読み飛ばして頂いて構わない。 JavaScriptが巻き上げを採用している理由の1つが、関数内のスコープ、変数を守るためと言われている。 JavaScriptの巻き上げによって、関数の先頭に「var x」が宣言されたのと同じになり、 先に宣言されたグローバル変数のxの値が混入するのを防いでいる。そんな理由らしいが納得はいかない。最初に変数宣言する癖を付けた方がいい。

また、関数にも巻き上げがあり、下コードのaa関数をfunctionより前に書いても実行される。この特徴は憶えておこう。

巻き上げはグローバル汚染から変数を守る

巻き上げはグローバル汚染から変数を守る

▼参考図書、サイト

 「JavaScriptの絵本 第2版 -Webプログラミングを始める新しい9つの扉-」 アンク 翔泳社
【JavaScript】var / let / const を本気で使い分けてみた  Qiita
【JavaScript】 変数・関数の巻き上げってなんだ? けーちゃんのプログラム開発ノート