厳格モード
JavaScriptはもともと、文法エラーがあっても処理を続行しようとする寛容な特性を持っています。
しかし、この特性によってデバッグが難しくなるという問題があり、それを補い、より安全なコーディングを行うために厳格モード(Strict mode)が導入されました。
JavaScriptの厳格モード(strict mode)の概念と、その利用目的について、次の目次に沿って解説します。
厳格モードの概要
厳格モードとは何か?
厳格モードは、JavaScriptコードの実行時に発生する一部の問題を検出し、エラーを減らすための特別なモードです。
このモードを使用すると、JavaScriptコードに対してより厳密なエラーチェックが適用されます。厳格モードは、スクリプトや関数の先頭に"use strict"
ディレクティブを記述することで宣言できます。
"use strict";
// strict modeが適用されるコード
厳格モードの使用目的
厳格モードの主な目的は、コードの品質を向上させ、エラーを減らして安全な開発環境を提供することです。JavaScriptは柔軟な言語であり、暗黙的な型変換やエラー処理の機能が多くありますが、これが時に意図しない結果を招くことがあります。厳格モードはそのような曖昧な部分を明確化し、予期せぬエラーを減らすことでコードの信頼性を高めます。
"use strict";
function exampleFunction() {
nonDeclaredVar = 10; // ReferenceError: nonDeclaredVar is not defined
}
exampleFunction();
このコードは、厳格モードを使用して作成された関数exampleFunction
を示しています。
"use strict"
は、厳格モードを宣言するディレクティブです。"use strict"
をスクリプトや関数の先頭に記述すると、そのスコープ内で厳格モードが適用されます。function exampleFunction() { ... }
は、exampleFunction
が厳格モードで実行される関数であることを示しています。したがって、関数内のコードは厳格モードのルールに従って動作します。nonDeclaredVar = 10;
:ここは問題を引き起こす部分です。nonDeclaredVar
という変数を宣言せずに値を代入しようとしたため、厳格モードではエラーが発生します。厳格モードでは、変数を宣言せずに使用することを禁止しています。exampleFunction()
:exampleFunction
を呼び出す部分です。関数が呼び出されると、内部のコードが実行されます。
このコード例では、"use strict"
によって厳格モードが適用されており、関数内で暗黙的に宣言されていない変数を使用しようとしたため、ReferenceError
が発生します。このように厳格モードを使用することで、ミスやエラーを事前に防ぎ、コードの安全性を高めることができます。
厳格モードを使うべき理由は何か?
- エラーの減少とデバッグの容易さ:厳格モードはミスやエラーを事前に防ぎ、ランタイムエラーを減らします。これにより、開発段階でのデバッグが容易になります。
- セキュリティ強化:厳格モードはセキュリティの強化に役立ちます。予期しない動作を防ぎ、悪意のあるコードの実行を困難にします。
- 可読性の向上:変数の明示的な宣言や初期化、重複した引数名の防止などにより、コードの可読性が向上します。
- モダンなコード習慣:厳格モードは現代的なJavaScript開発の重要な一部であり、モダンなコード習慣を身につけるのに役立ちます。
厳格モードの有効化方法
JavaScriptで厳格モードを有効にする方法はいくつかあります。
"use strict"
ディレクティブを使用して- スクリプト全体に厳格モードを適用するか、
- 特定の関数内でのみ厳格モードを有効化することも可能です。
- モジュールでは厳格モードがデフォルトで適用されます。
ご注意ください!
波括弧{}
で囲まれたブロック文の内部では、厳格モード(Strict mode)は動作しません。
例えば、if
、for
、{}
などの一般的なブロックで"use strict"
ディレクティブを使用しても効果はありません。
"use strict"
ディレクティブの役割
"use strict"
ディレクティブは厳格モードを有効化する役割を持ちます。このディレクティブをスクリプトや関数の先頭に置くと、その下のコードには厳格モードが適用されます。
以下は"use strict"
ディレクティブの使用例です。
"use strict"
// ここから厳格モードが適用されます。
スクリプト全体に厳格モードを適用する方法
スクリプト全体に厳格モードを適用するには、スクリプトファイルの先頭に"use strict"
を追加します。これにより、そのスクリプトファイル全体で厳格モードが有効になります。
"use strict";
// このファイル全体に厳格モードが適用されます。
関数内に厳格モードを適用する方法
特定の関数内でのみ厳格モードを有効化するには、その関数内の先頭に"use strict"
を追加します。これにより、その関数内だけ厳格モードが適用されます。
function myFunction() {
"use strict";
// 厳格モードはこの関数内のみ適用されます。
}
関数内に厳格モードを適用すると、その関数内だけ厳格なルールが適用されるため、他の関数やスクリプトには影響を与えません。
モジュールは基本的に厳格モードが適用されています
JavaScriptモジュールの全内容は自動的に厳格モードとなるため、それを開始するための文は不要です。
<script type="module">
function myStrictFunction() {
// モジュールであるため、基本的に厳格モードが適用されます。
}
export default myStrictFunction;
</script>
厳格モードの動作原理
JavaScriptで厳格モードを使用した場合と使用しなかった場合の主な違いは以下の通りです。
機能/状況 | 厳格モード使用時 | 厳格モード未使用時 |
---|---|---|
暗黙のグローバル変数禁止 | 変数を事前に宣言せずに使用するとエラーが発生します。 | 変数を事前に宣言せずに使用してもエラーは発生しません。 |
割り当て不可能なプロパティへの代入禁止 | オブジェクトの拡張不可能なプロパティに値を代入しようとするとエラーが発生します。 | 拡張不可能なオブジェクトに値を代入してもエラーは発生しません。 |
重複した引数名の禁止 | 関数で重複した引数名を使用するとエラーが発生します。 | 関数で重複した引数名を使用してもエラーは発生しません。 |
通常の関数実行時のthis の値の設定 |
通常の関数内でthis はグローバルオブジェクトではなくundefined に設定されます。 |
通常の関数内で呼び出しコンテキストが設定されていない場合、this はグローバルオブジェクトを参照します。 |
暗黙のグローバル変数禁止
機能/状況 | 厳格モード使用時 | 厳格モード未使用時 |
---|---|---|
暗黙のグローバル変数禁止 | 変数を事前に宣言せずに使用するとエラーが発生します。 | 変数を事前に宣言せずに使用してもエラーは発生しません。 |
"use strict"
function exampleStrict() {
strictVar = 10; // ReferenceError: strictVar is not defined
}
exampleStrict();
上記のコードでstrictVar
という変数を事前に宣言せずに使用しようとすると、厳格モードではReferenceErrorが発生します。これは厳格モードが、変数を明示的に宣言しなければ暗黙のグローバル変数として扱うことを防止するためです。
function exampleNonStrict() {
nonStrictVar = 20; // No error、暗黙的にグローバル変数として処理される
}
exampleNonStrict();
console.log(nonStrictVar); // 20
上記のコードでは厳格モードを使用していないため、nonStrictVar
変数を事前に宣言せずに使用してもエラーは発生しません。この場合、nonStrictVar
は暗黙的にグローバル変数として扱われますが、これはコードの予期しない動作を引き起こす可能性があり、リスクを伴います。
割り当て不可能なプロパティへの代入禁止
機能/状況 | 厳格モード使用時 | 厳格モード未使用時 |
---|---|---|
割り当て不可能なプロパティへの代入禁止 | オブジェクトの拡張不可能なプロパティに値を代入しようとするとエラーが発生します。 | 拡張不可能なオブジェクトに値を代入してもエラーは発生しません。 |
"use strict"
const sealedObject = Object.seal({ prop: 10 });
// 厳格モードでは、拡張不可能なオブジェクトにプロパティを追加しようとするとエラーが発生します。
sealedObject.newProp = 20; // TypeError: Cannot add property newProp, object is not extensible
上記のコードではObject.seal()
メソッドを使ってオブジェクトをシール(密封)しています。厳格モードでは、このようにシールされたオブジェクトに新しいプロパティを追加しようとするとTypeErrorが発生します。
const nonStrictSealedObject = Object.seal({ prop: 10 });
// 厳格モードでなければ、拡張不可能なオブジェクトに値を代入してもエラーは発生しません。
nonStrictSealedObject.newProp = 20; // No error、新しいプロパティがオブジェクトに追加されます
上記のコードでは厳格モードを使用していないため、拡張不可能なオブジェクトにプロパティを代入しようとしてもエラーは発生せず、新しいプロパティがオブジェクトに追加されます。これは予期しない動作を引き起こす可能性があり、厳格モードを使用することでこれを防ぐことができます。
重複した引数名の禁止
機能/状況 | 厳格モード使用時 | 厳格モード未使用時 |
---|---|---|
重複した引数名の禁止 | 関数で重複した引数名を使用するとエラーが発生します。 | 関数で重複した引数名を使用してもエラーは発生しません。 |
"use strict"
function strictExample(param1, param1) {
console.log(param1);
}
strictExample(10, 20); // SyntaxError: Duplicate parameter name not allowed in this context
上記のコードでは、strictExample
関数の引数param1
が重複して宣言されています。厳格モードでは、関数の引数名が重複するとSyntaxErrorが発生します。
function nonStrictExample(param1, param1) {
console.log(param1);
}
nonStrictExample(10, 20); // 20 (2番目の引数の値)
上記のコードでは厳格モードを使用していないため、関数の引数名が重複してもエラーは発生しません。実際に、2番目の引数の値が出力されることが確認できます。
通常関数実行時のthis
の値の設定
機能/状況 | 厳格モード使用時 | 厳格モード未使用時 |
---|---|---|
通常関数実行時のthis の値の設定 |
通常関数内でのthis はグローバルオブジェクトではなく、undefined に設定されます。 |
通常関数内で呼び出しコンテキストが設定されていない場合、this はグローバルオブジェクトを参照します。 |
"use strict"
function strictFunction() {
return this;
}
console.log(strictFunction()); // undefined
上記のコードでは、厳格モードで関数strictFunction
を呼び出すと、this
はundefined
を指します。厳格モードでは、関数の呼び出しコンテキストを変更せず、this
をundefined
に設定します。
function nonStrictFunction() {
return this;
}
console.log(nonStrictFunction()); // グローバルオブジェクト(ブラウザ環境では window)
上記のコードでは、非厳格モードで関数nonStrictFunction
を呼び出すと、this
はグローバルオブジェクトを指します。非厳格モードでは、関数の呼び出しコンテキストが設定されていない場合、this
はグローバルオブジェクトを参照します。
コード品質向上のための厳格モード活用
厳格モードを活用してコード品質を向上させることは非常に重要です。
ミスやエラーを最小限に抑え、コードの保守性を向上させる
厳格モードは、コード内の一部のミスやエラーを事前に予防し検出できるようにサポートします。これにより、コードを作成する過程で発生しうるエラーを減らし、デバッグ時間を節約できます。変数の事前宣言と初期化、重複したパラメータ名の防止などにより、コードの安定性を高め、それがコードの保守性向上に寄与します。
厳格モードを適用したコードの可読性向上事例
厳格モードはコードの可読性向上にも役立ちます。変数を事前に宣言し初期化することや、明示的なthis
の使用はコードの動作を明確に説明し、理解しやすいコードを実現します。
"use strict"
// 厳格モードを適用しない場合
var globalVar = 10;
function someFunction(x) {
y = x * 2; // エラーが発生する可能性があります
return y;
}
// 厳格モードを適用した場合
var globalVar = 10;
function someFunction(x) {
var y = x * 2; // 変数を明示的に宣言
return y;
}
上の例では、厳格モードを使用した場合、変数の明示的な宣言と初期化が強調されており、可読性が向上していることが確認できます。
このような方法を活用することで、コードの品質と可読性を向上させることができます。厳格モードは、ランタイムエラーを減らして安全性を高めるだけでなく、コードの意図を明確に表現し、保守を容易にするツールとして非常に有用です。
仕様書
仕様書 | |
---|---|
"use strict"
|
The Strict Mode of ECMAScript |
ブラウザ互換性
ディレクティブ |
デスクトップ Chrome
|
デスクトップデスクトップ Edge
|
デスクトップ Firefox
|
Safari
|
---|---|---|---|---|
"use strict"
|
13 | 10 | 4 | 6 |