ChromeやNodeJSのJavascriptコンソール画面で動作確認する場合、
以下の様に間違ってエラーになってしまうことがあります。
const obj = JSON.parse(""); // JSON形式じゃない文字列を指定
// Uncaught SyntaxError: Unexpected end of JSON input
JSON形式の文字列で指定するところに空文字を指定した場合ですが、Uncaught SyntaxErrorとなってしまいます。
じゃあ間違えたのだからと訂正して再度実行すると
const obj = JSON.parse("[]"); // JSON形式の文字列を指定
// Uncaught SyntaxError: Identifier 'obj' has already been declared
既に宣言済みなのでエラーとなります。
それでは、既に宣言済みなら変数が存在するのだと思って参照してみると
console.log(obj);
// Uncaught ReferenceError: obj is not defined
宣言されていないとエラーとなります。
グローバルに変数が残っているかなと思ってdeleteを実行しても消えている様子は無いです。
delete obj;
// false
const obj = JSON.parse("[]");
// Uncaught SyntaxError: Identifier 'obj' has already been declared
MDNのlet変数やconst変数の説明を見てみるとTemporal dead zoneの存在について紹介されています。
undefined の値で始まる var 変数と異なり、 let 変数は定義が評価されるまで初期化されません。変数を宣言より前で参照することは ReferenceError を引き起こします。ブロックの始めから変数宣言が実行されるまで、変数は "temporal dead zone" の中にいるのです。
どうやら、宣言されたconstやlet変数はTemporal dead zoneの中に残ってしまっていて参照できない状態になっているようです。
エラーが発生するなどして変数の初期化が行われなかった場合、letやconstについてはTemporal dead zoneに変数があるため、宣言はされているが、参照出来ない状態となるらしいです。この状態だと変数を再使用することは出来なくなってしまいます。
varの場合だと変数を宣言する前に呼び出すとundefinedが取得されます。
console.log(pizza);
var pizza = 'Deep Dish 🍕🍕🍕';
// undefined
letの場合だと変数を宣言する前に呼び出すとUncaught ReferenceErrorとなり変数が取得できません。
console.log(pizza);
let pizza = 'Deep Dish 🍕🍕🍕';
// Uncaught ReferenceError: Cannot access 'pizza' before initialization
変数pizzaはTemporal dead zoneから取り出せずもう使用することは出来なくなってしまいます。
- [let - JavaScript | MDN]
(https://developer.mozilla.org/ja/docs/Web/JavaScript/Reference/Statements/let) - Chrome console already declared variables throw undefined reference errors for let
- Temporal Dead Zone ☠️ | Wes Bos
対応策としては、
リロードなどをして最初から実行し直すか、
もしくは、varを使うか、
var obj = JSON.parse("");
// Uncaught SyntaxError: Unexpected end of JSON input
var obj = JSON.parse("");
// Uncaught SyntaxError: Unexpected end of JSON input
もしくはスコープを指定するか、
{
const obj = JSON.parse("");
}
もしくはletを使っていったん宣言だけすれば最初にundefinedがセットされます。
let obj;
// undefined
obj = JSON.parse("");
// Uncaught SyntaxError: Unexpected end of JSON input
obj = JSON.parse("");
// Uncaught SyntaxError: Unexpected end of JSON input
闇の魔術とはちょっと違うかも知れないけれど、Temporal dead☠️ zoneの呼び方が闇っぽいのでここに載せておきました。
と思っていたら、The Temporal Dead Zone and the Deathly Hallows(Temporal Dead Zoneと死の秘宝)と呼んでいる記事があったのでタイトルも合わせて変えました。