JavaScriptのスコープとは?var・let・constの違いを解説

JavaScriptを学習するうえで欠かせない概念のひとつが「スコープ」です。
スコープを正しく理解していないと、意図しないバグや予期しない挙動につながることがあります。
本記事では、JavaScriptのスコープの基本から、var・let・constの違いまでを、初心者でも確実に理解できるように解説します。
Contents
スコープとは何か
スコープとは、「変数や関数が有効になる範囲」のことです。
同じ名前の変数であっても、スコープが異なれば別のものとして扱われます。
スコープの基本イメージ
// scope-basic.js
const message = "グローバル";
function showMessage() {
const message = "ローカル";
console.log(message);
}
showMessage(); // ローカル
console.log(message); // グローバルこの例では、同じ message という名前でも、関数内と外で別の値として扱われています。
これがスコープの基本的な考え方です。
スコープの種類
JavaScriptには主に以下の3つのスコープがあります。
- グローバルスコープ
- 関数スコープ
- ブロックスコープ
それぞれ順番に見ていきます。
グローバルスコープ
特徴
- どこからでもアクセスできる
- スクリプト全体で共有される
// global-scope.js
const globalValue = "どこからでも使える";
function test() {
console.log(globalValue);
}
test(); // どこからでも使えるグローバル変数は便利ですが、多用するとバグの原因になります。
予期せぬ上書きや競合が起きやすいため、必要最低限にすることが重要です。
関数スコープ
特徴
- 関数内で宣言された変数は外からアクセスできない
varは関数スコープを持つ
// function-scope.js
function test() {
var message = "関数内";
console.log(message);
}
test(); // 関数内
console.log(message); // エラー関数の外からはアクセスできないため、安全にデータを扱うことができます。
ブロックスコープ
特徴
{}(ブロック)単位で有効letとconstが対象
// block-scope.js
if (true) {
let message = "ブロック内";
console.log(message);
}
console.log(message); // エラーifやforなどのブロック内で定義された変数は、外では使えません。
var・let・constの違い
スコープの理解とセットで重要なのが、変数宣言の違いです。
varの特徴
関数スコープを持つ
// var-scope.js
function test() {
if (true) {
var value = 10;
}
console.log(value); // 10
}
test();varはブロックを無視して、関数全体で有効になります。
再宣言できる
// var-redeclare.js
var count = 1;
var count = 2;
console.log(count); // 2同じ名前で再宣言できるため、バグの原因になりやすいです。
巻き上げ(ホイスティング)が発生する
// var-hoisting.js
console.log(value); // undefined
var value = 10;宣言が先に処理されるため、エラーにならず undefined になります。
letの特徴
ブロックスコープを持つ
// let-scope.js
if (true) {
let value = 10;
}
console.log(value); // エラーブロック外ではアクセスできません。
再宣言できない
// let-redeclare.js
let count = 1;
// let count = 2; // エラー同じスコープ内での再宣言は禁止されています。
ホイスティングはされるが使えない(TDZ)
// let-tdz.js
// console.log(value); // エラー
let value = 10;宣言前にアクセスするとエラーになります。
この期間を「TDZ(Temporal Dead Zone)」と呼びます。
constの特徴
ブロックスコープを持つ
// const-scope.js
if (true) {
const value = 10;
}
console.log(value); // エラーletと同様にブロックスコープです。
再代入できない
// const-reassign.js
const value = 10;
// value = 20; // エラー一度代入した値は変更できません。
オブジェクトや配列は変更可能
// const-object.js
const user = { name: "Taro" };
user.name = "Jiro";
console.log(user.name); // Jiro参照は固定ですが、中身の変更は可能です。
var・let・constの使い分け
実務では以下のルールが一般的です。
- 基本は
const - 再代入が必要な場合のみ
let varは基本的に使用しない
理由
- 意図しない再代入を防げる
- スコープが明確になる
- バグを減らせる
よくあるバグと注意点
ループ内のvarによる問題
// var-loop.js
for (var i = 0; i < 3; i++) {
setTimeout(() => {
console.log(i);
}, 100);
}結果:
3
3
3letで解決
// let-loop.js
for (let i = 0; i < 3; i++) {
setTimeout(() => {
console.log(i);
}, 100);
}結果:
0
1
2スコープ理解に役立つ内部リンク
スコープの理解は、JavaScript全体の基礎理解につながります。
以下の記事もあわせて確認することで、より理解が深まります。
- JavaScriptの基本構造とは?初心者向けに仕組みを解説
- JavaScriptの関数とは?基本から使い方まで解説
- JavaScriptのコールバック関数とは?基本から実践まで徹底解説
- JavaScriptの非同期処理とは?Promiseとasync/awaitの基礎
まとめ
JavaScriptのスコープは、変数の有効範囲を決める重要な仕組みです。
- スコープには「グローバル・関数・ブロック」がある
varは関数スコープで扱いが難しいletとconstはブロックスコープで安全- 基本は
const、必要に応じてletを使う
スコープを正しく理解することで、予期しないバグを防ぎ、安定したコードを書くことができます。

