【JavaScript】とてもややこしいスコープチェーン
スコープチェーンについてメモします。
スコープチェーンの検索は、このように最初に発見した値を返します。
xの中身が上書きされていくということは大体想像が付きます。
処理を括るクロージャーの考えを踏まえると、
関数の外でxを呼んだ場合グローバルでxに代入したfalseが出力されます。
ここまではそんなにややこしいことはないのですが、
次の例からややこしくなっていきます。
ややこしや~
上から順に、まずグローバルで変数aに1を代入していますね。
次に変数funcにaをコンソール出力させる関数を代入してます。
次に即時関数内で、変数aに今度は100を代入させます。
※ (); ←これは関数を即時に実行させます。
次にfを実行していますが、fは引数で、
最後の行で引数に二行目で定義したfunc関数を渡しています。
ということで、即時関数内でfunc関数を実行しているわけですが、 先ほどのようにスコープチェーンの検索の仕方と、クロージャーの考えを踏まえると
同じ関数内で変数aに100を上書きしているため、コンソールで出力されるのは100じゃないかなと思います。(私はそう思いました)
ですが、ログで出力されるのはなんとグローバルで代入した1を出力するのです。
これはスコープは関数実行時ではなく、定義時に決められる為なのです。
二行目の
var func = function() { console.log(a); };
ここで定義した時点で、aはスコープチェーンの検索で一行目のvar a = 1;を見ているのです。
なので、この関数を呼び出した関数内のaはスルーされたのでした。
スコープは関数実行時ではなく、定義時に決められる
これが分かってないと出くわした際に躓いてしまいそうですね。