カテゴリー
JavaScript

スコープチェーン

JavaScriptは構文スコープを持つ言語
変数のスコープは、変数が定義されているソースコード行の集合と考えられる。
グローバル変数は、プログラム全体で有効
ローカル変数は、宣言された関数全体と、その関数内に入れ子にされた関数群全体で有効

JavaScriptのコードには、そのコードに関連付けられたスコープチェーンが存在すると考えられる。
このスコープチェーンとは、そのコードに対して「スコープ内」にある変数を定義するオブジェクトのリスト(=チェーン)のこと。

JavaScriptが変数xの値を調べる必要がある場合(この処理を変数の名前解決と呼ぶ)チェーンの先頭のオブジェクトから検索を始める。
このオブジェクトがxという名前のプロパティを持つ場合、そのプロパティの値が使われる。
最初のオブジェクトがxという名前のプロパティを持たない場合、チェーンの次のオブジェクトに対して検索を行い、
次へ次へと検索を進めていく。
スコープチェーンのどのオブジェクトにもxという名前のプロパティが存在しない場合、ReferenceErrorが発生する。

トップレベルコード中(関数に含まれていないコード部分)では、
スコープチェーンに含まれるオブジェクトはグローバルオブジェクト1つだけ。
入れ子になっていない関数の場合、スコープチェーンには、2つのオブジェクトが含まれる。

先頭のオブジェクトには、関数の引数やローカル変数が定義され、
2番目のオブジェクトがグローバルオブジェクト

入れ子になった関数では、3個以上のオブジェクトが含まれる。
このオブジェクトのチェーンは次のように作成される。
まず、関数が定義された時に、現在有効なスコープチェーンを保存しておく。
関数が呼び出された時には、新たにオブジェクトを生成し、ローカル変数を保存する。
そして、この新しいオブジェクトを保存しておいたスコープチェーンに追加し、
関数呼び出し時のスコープチェーンを表す新たなスコープチェーンを生成する。
入れ子にされた関数の場合、外側の関数が呼び出されるたびに、内側の関数が再び定義される。

参考書籍:

オライリー JavaScript 第6版

カテゴリー
JavaScript

関数のスコープとホイスティング(巻き上げ)

JavaScriptにはブロックスコープがない。
C言語などは、ブロックスコープ。
変数は宣言された中括弧で囲まれたブロックの外からは見えなくなる。

JavaScriptでは、代わりに関数スコープを使っている。
変数は、その変数が定義された関数と、その関数に入れ子にされている関数中からアクセスできる。
関数中で宣言された変数はすべて関数全体からアクセスできる。
関数の外側からはアクセスできない。
関数の外側で宣言された変数はグローバル変数になり、プログラム全体からアクセスできる。

ホイスティング(巻き上げ)
変数宣言よりも前のコードからもアクセスできる。

var scope = "global";
function f() {
    console.log(scope);     //undefined globalではない  ホイスティング(巻き上げ)
    var scope = "local";    //ここでローカル変数を初期化
    console.log(scope);     //local
}

ブロックスコープを持つプログラミング言語では、
変数を利用する場所のできるだけ近くで宣言するようにして、
スコープをできるだけ狭くすることがよいと一般的にされている。
一方、JavaScriptはブロックスコープがないので、
すべての変数を関数の先頭で宣言するようにして、
スコープとソースコードが同じになり、コードがわかりやすくなる。

参考書籍:

オライリー JavaScript 第6版

カテゴリー
JavaScript

変数のスコープ

var文
ローカル変数は、var文で宣言しなければならない。
グローバル変数はvar文を省略できる。

参考書籍:

オライリー JavaScript 第6版

カテゴリー
JavaScript

変数の宣言

変数は、その変数を使用する前に宣言すべき。
初期値を宣言しなかった変数は、何かの値が代入されるまでundefinedとなる。

参考書籍:

オライリー JavaScript 第6版

カテゴリー
JavaScript

グローバルオブジェクト

グローバルオブジェクトのプロパティは、グローバルに定義された名前となり、プログラム中のどこからでも利用できる。

参考書籍:

オライリー JavaScript 第6版

カテゴリー
JavaScript

nullとundefined

null
オブジェクトが存在しないことを表す特別なオブジェクト値

undefined
未定義
初期化されていない変数の値
存在しないオブジェクトプロパティや配列の要素を読み出したときの値
戻り値がない関数が返す値

undefinedはシステムレベルで予期せぬ、ある意味、エラーのような場合を表すもの
nullはプログラムレベルで予定どおりの場合を表すもの
nullを使うようにする。

参考書籍:

オライリー JavaScript 第6版

カテゴリー
JavaScript

論理値

true False

参考書籍:

オライリー JavaScript 第6版

カテゴリー
JavaScript

パターンマッチング

JavaScriptには、テキストパターンを表すオブジェクトを生成するために、
RegExp()コンストラクタが定義されている。
このパターンは、正規表現を使って記述する。

テキスト処理において、よく使われる強力なツール。
RegExpは基本的な型ではない。
JavaScriptプログラム中に直接記述するためのリテラル形式の文法が用意されている。

参考書籍:

オライリー JavaScript 第6版

カテゴリー
JavaScript

文字列の操作

+で文字列の連結ができる。
文字列の長さは、その文字列のlengthプロパティで調べることができる。

s.lenght

その他にも、文字列に対して呼び出すことができるメソッドが数多くある。

JavaScriptでは文字列は不変。
replace()、toUpperCase()などのメソッドは、新しい文字列が返され、メソッドを呼び出した文字列は変更されない。

ECMAScript5では、文字列呼び出しのみの配列のように扱うことができる

s = "hello, world";
s[0]    //h
s[s.lenght-1]   //d

参考書籍:

オライリー JavaScript 第6版

カテゴリー
JavaScript

文字列リテラルのエスケープシーケンス

文字列を単一引用符で囲んでいる場合は、英語の短縮形や所有格に注意する。

'You\'re right, it can\'t be a quote'

参考書籍:

オライリー JavaScript 第6版