Core JavaScript 1.5 Guide:Core Language Features
出典: MDC
目次 |
[編集] 値
JavaScript は以下の値の型を認識します。
- 数値:42 や 3.14159 など
- 論理値(真偽値):
trueまたはfalse - 文字列:"Howdy!" など
-
null:null 値を意味する特殊なキーワード。nullはプリミティブ値でもある。JavaScript は大文字・小文字を区別するため、nullはNullやNULLなどとは異なる。 -
undefined:その値が未定義であるトップレベルプロパティ。undefinedはプリミティブ値でもある。
このように値の型、すなわちデータ型の種類が比較的少ないことで、アプリケーションで便利な関数を実行することができます。整数と実数をはっきりと区別するということはありません。JavaScript にははっきりとした日付を示すデータ型もありません。しかし、Date オブジェクトとそのメソッドを使うことで日付を扱うことができます。
オブジェクト と 関数 も言語において基本的な要素です。オブジェクトを値の名前付きコンテナとして、関数をアプリケーションが実行できる手続きとして考えることができます。
[編集] データ型の変換
JavaScript は動的型付け言語です。そのため、変数宣言時にデータ型を指定する必要が無く、またスクリプト実行時に必要に応じてデータ型が自動的に変換されます。例えば以下のように変数を定義したとします。
var answer = 42;
その後に、同じ変数に文字列を代入できます。
answer = "Thanks for all the fish...";
JavaScript は動的型付けであるためにこの代入時にエラーメッセージは出ません。
数値と文字列が + 演算子で結合された式では、JavaScript は数値を文字列に変換します。以下の式を見てみましょう。
x = "The answer is " + 42 // "The answer is 42" を返す y = 42 + " is the answer" // "42 is the answer" を返す
それ以外の演算子がある式では、JavaScript は数値を文字列に変換しません。
"37" - 7 // 30 を返す "37" + 7 // "377" を返す
[編集] 変数
アプリケーションで値を識別する名前として変数を使用します。変数の名前はあるルールに従って付けなくてはなりません。変数の名前は識別子とも呼ばれます。
JavaScript の識別子は必ずアルファベットかアンダースコア (_) かドル記号 ($) から始まらなくてはなりません。続く文字は数字 (0-9) も使えます。JavaScript は大文字・小文字を区別するため、使えるアルファベットは "A" から "Z"(大文字)と "a" から "z"(小文字)です。
JavaScript 1.5 からは å や ü といった ISO 8859-1 や Unicode のアルファベットも識別子に使えます。Unicode エスケープシーケンス のページに列挙されている \uXXXX 形式の Unicode エスケープシーケンスも識別子に使用できます。
Number_hits や temp99 や _name が使用できる名前の例です。
[編集] 変数の宣言
2 つの方法で変数を宣言できます。
- var というキーワードを使う。例えば、
var x = 42。この構文は ローカルおよびグローバル 変数どちらの宣言にも使用可能です。 - 単に値を代入する。例えば、
x = 42。これはいつでも グローバル変数 を宣言できますが、厳格な JavaScript 警告 (strict JavaScript warning) が発生します。この方法は使用すべきではありません。
[編集] 変数の評価
var 文を使用し、初期化せずに宣言された変数は undefined の値をとります。
未宣言の変数にアクセスしようとすると、ReferenceError 例外が投げられます。
var a;
print("a の値は " + a); // "a の値は undefined" を出力
print("b の値は " + b); // ReferenceError 例外を投げる
undefined を使うと変数に値が入っているかどうかを確かめられます。以下のコードでは、変数 input には値が代入されておらず、if 文での評価結果は true です。
var input;
if(input === undefined){
doThis();
} else {
doThat();
}
undefined は真偽値コンテキストで使用されると false として振る舞います。例えば以下のコードでは、myArray の要素が未定義であるために関数 myFunction が実行されます。
var myArray = new Array(); if (!myArray[0]) myFunction();
null 変数を評価すると、数値コンテキストにおいては null 値は 0 として振る舞います。また、真偽値コンテキストでは false として振る舞います。
var n = null; print(n * 32); // prints 0
[編集] 変数のスコープ
変数を関数の外側で宣言すると、その変数はその文書のどのコードからも使用できるようになるため、グローバル(大域)変数と呼ばれます。変数を関数の内部で宣言すると、その変数はその関数の中でしか使用できないため、ローカル(局所)変数と呼ばれます。
JavaScript には ブロック文 のスコープがありません。むしろ、そのブロックを内包しているコードに対して局所化されます。例えば以下のコードは condition が false のとき、例外を投げずに 0 が出力されます。
if (condition) {
var x = 5;
}
print(x ? x : 0);
JavaScript の変数に関する独特なこととして、後に宣言される変数を例外を発生させることなく参照できるというのも挙げられます。
print(x === undefined); // "true" を出力 var x = 3;
[編集] グローバル変数
グローバル変数は実際にはグローバルオブジェクトのプロパティです。ウェブページではグローバルオブジェクトは window です。そのため、window.variable という構文を使うことでグローバル変数をセットしたり、グローバル変数にアクセスしたりすることができます。
したがって、あるウィンドウやフレームで宣言したグローバル変数に、そのウィンドウやフレームの名前を指定すれば別のウィンドウやフレームからアクセスできます。例えば、phoneNumber という変数を FRAMESET 文書内で宣言すると、子フレームから parent.phoneNumber としてこの変数を参照することができます。
[編集] 関連項目
[編集] 定数
const キーワードを使うことで、読み取り専用の名前付き定数を作ることができます。定数識別子の構文は変数識別子のそれと同じです。識別子はアルファベットまたはアンダースコアから始まらなくてはならず、全体としてはアルファベット、数字、アンダースコアからなるようにします。
const prefix = '212';
定数は代入によって値を変えたり、スクリプト実行中に再宣言したりすることはできません。
定数のスコープルールは、const キーワードがグローバル定数でさえも常に必須であることを除いて、変数のそれと同じです。このキーワードを省略すると、その識別子は変数を表すと見なされます。
同一スコープ内で、関数や変数と同じ名前の定数を宣言することはできません。
// この場合、エラーが発生
function f() {};
const f = 5;
// この場合もエラーが発生
function f() {
const g = 5;
var g;
// 文
}
[編集] リテラル
JavaScript では値を表すのにリテラルを使います。これは固定された値で、変数ではありません。あなたがスクリプト中に直接記述する値のことです。このセクションでは以下の種類のリテラルについて説明します。
[編集] 配列リテラル
配列リテラルとは、ゼロ個以上の式のリストであり、おのおのの式が配列の要素を表しており、角括弧 ([]) でくくられているもののことです。配列リテラルを使って配列を作ると、その配列は指定された値で要素を初期化され、配列の長さは指定された引数の個数にセットされます。
以下の例では、3 つの要素を持ち、長さが 3 の coffees という配列を作ります。
var coffees = ["French Roast", "Colombian", "Kona"];
注意 配列リテラルはオブジェクト初期化子の一種です。オブジェクト初期化子の使用 を参照してください。
トップレベルのスクリプト内でリテラルを用いて配列を作った場合、JavaScript は配列リテラルを含む式を評価するたびに配列を解釈します。さらに関数内で使用されたリテラルは関数が呼び出されるたびに生成されます。
配列リテラルも Array オブジェクトです。Array オブジェクトの詳細は Array オブジェクト をご覧ください。
配列リテラルでの余計なコンマ
配列リテラルではすべての要素を指定する必要はありません。立て続けに 2 つのコンマを置くと、未指定の要素のための空間を持った配列が生成されます。次の例では fish という配列を作ります。
var fish = ["Lion", , "Angel"];
この配列は値を持つ 2 つの要素と 1 つの空の要素を持っています(fish[0] は "Lion"、fish[1] は undefined、fish[2] は "Angel")。
要素のリストの最後にコンマを付けた場合、そのコンマは無視されます。次の例では配列の長さは 3 です。myList[3] は存在しません。リストの他のすべてのコンマは新しい要素を示します。
var myList = ['home', , 'school', ];
次の例では配列の長さは 4 です。myList[0] と myList[2] が抜けています。
var myList = [ , 'home', , 'school'];
次の例では配列の長さは 4 です。myList[1] と myList[3] が抜けています。最後のコンマのみが無視されます。
var myList = ['home', , 'school', , ];
[編集] 真偽値リテラル
真偽値型は true と false、2 つのリテラル値があります。
プリミティブな真偽値の true と false を Boolean オブジェクトの true や false という値と混同してはいけません。Boolean オブジェクトはプリミティブな真偽値型のラッパです。詳細は Boolean オブジェクト を参照してください。
[編集] 整数
整数は 10 進数、16 進数、8 進数で表現可能です。10 進整数リテラルは先頭の 0(ゼロ)を除いた、数字の連続からなります。整数リテラルにおいて先頭の 0(ゼロ)はそれが 8 進数であるということを指します。先頭の 0x(または 0X)は 16 進数を指します。16 進整数は数字(0 から 9)と a から f および A から F のアルファベットからなります。8 進整数は 0 から 7 までの数字のみからなります。
8 進整数リテラルは廃止予定であり、ECMA-262 第 3 版から除かれています。JavaScript 1.5 では依然として後方互換のためにそれをサポートしています。
整数リテラルの例は以下のようなものです。
0、117、-345(10 進数) 015、0001、-077(8 進数) 0x1123、0x00111、-0xF1A7(16 進数)
[編集] 浮動小数点リテラル
浮動小数点リテラルは以下の部分からなります。
- 整数部(先頭に "+" や "-" の符号を付けてもよい)
- 小数点 (".")
- 小数部
- 指数部
指数部は "e" または "E" の後に整数が続く形です。整数の先頭には符号("+" や "-")を付けることができます。浮動小数点リテラルは少なくとも 1 つの数字と、小数点もしくは "e"(または "E")からなる必要があります。
3.1415、-3.1E12、.1e12、2E-12 というのが浮動小数点リテラルの例です。
より簡潔に書けば、 次の形式です。
[digits][.digits][(E|e)[(+|-)]digits]
例:
3.14 2345.789 .3333333333333333333
[編集] オブジェクトリテラル
オブジェクトリテラルとは、ゼロ個以上のプロパティ名とそれに結びつけられた値のペアのリストであり、波括弧 ({}) でくくられているものです。オブジェクトリテラルを文の最初に使わないようにしてください。{ がブロックの始まりと解釈され、エラーを引き起こしたり、予期せぬ動作をしたりすることになります。
以下にオブジェクトリテラルの例を示します。car オブジェクトの最初の要素は myCar プロパティを定義します。2 番目の要素の getCar プロパティは関数を呼び出します (CarTypes("Honda"))。3 番目の要素の special プロパティは既存の変数を使用します (Sales)。
var Sales = "Toyota";
function CarTypes(name) {
if (name == "Honda")
return name;
else
return "Sorry, we don't sell " + name + ".";
}
var car = { myCar: "Saturn", getCar: CarTypes("Honda"), special: Sales };
document.write(car.myCar); // Saturn
document.write(car.getCar); // Honda
document.write(car.special); // Toyota
さらに、数値リテラルや文字列リテラルをプロパティ名に使用したり、オブジェクトをネストさせたりできます。以下の例ではこれらのオプションを使用しています。
var car = { manyCars: {a: "Saab", b: "Jeep"}, 7: "Mazda" };
document.write(car.manyCars.b); // Jeep
document.write(car[7]); // Mazda
以下のことに注意してください。
var foo = {a: "alpha", 2: "two"};
document.write(foo.a); // alpha
document.write(foo[2]); // two
//document.write(foo.2); // Error: missing ) after argument list
//document.write(foo[a]); // Error: a is not defined
document.write(foo["a"]); // alpha
document.write(foo["2"]); // two
[編集] 文字列リテラル
文字列リテラルとは、ゼロ個以上の文字を二重引用符 (") または単一引用符 (') でくくったものです。文字列は同じ種類の引用符でくくってください。つまり、どちらも単一引用符にするか、またはどちらも二重引用符にするかということです。以下が文字列リテラルの例です。
- "blah"
- 'blah'
- "1234"
- "one line \n another line"
- "John's cat"
文字列リテラルの値でなら、String オブジェクトのどんなメソッドでも呼び出すことができます。JavaScript が自動的に文字列リテラルを一時的な String オブジェクトに変換し、メソッドを呼び出し、その一時的な String オブジェクトを破棄するのです。String.length プロパティを文字列リテラルで使うこともできます。
- "John's cat".length
特に String オブジェクトを使う必要がない場合は文字列リテラルを使うようにしてください。String オブジェクトの詳細は String オブジェクト をご覧ください。
[編集] 文字列での特殊文字の使用
普通の文字に加えて、文字列では特殊文字も使えます。次の例をご覧ください。
"one line \n another line"
ここで、JavaScript の文字列で使用できる特殊文字の表を示します。
| 文字 | 意味 |
|---|---|
| \b | 後退 |
| \f | 改ページ |
| \n | 改行 |
| \r | 復帰 |
| \t | タブ |
| \v | 垂直タブ |
| \' | アポストロフィまたは単一引用符 |
| \" | 二重引用符 |
| \\ | バックスラッシュ (\) |
| \XXX | 0 から 377 までの 3 桁の 8 進数 XXX で指定された Latin-1 エンコーディングの文字。例えば、\251 は著作権記号を示す。 |
| \xXX | 00 から FF までの 2 桁の 16 進数 XX で指定された Latin-1 エンコーディングの文字。例えば、\xA9 は著作権記号を示す。 |
| \uXXXX | 4 桁の 16 進数 XXXX で指定された Unicode 文字。例えば、\u00A9 は著作権記号を示す。Unicode エスケープシーケンス を参照。 |
表 2.1:JavaScript の特殊文字
[編集] 文字のエスケープ
表 2.1 に載っていない文字の直前にバックスラッシュを付けても無視されますが、この使用法は廃止予定であり、使用を避けるべきです。
バックスラッシュを直前に付けることで引用符を文字列に挿入できます。これを「引用符をエスケープする」と言います。
var quote = "He read \"The Cremation of Sam McGee\" by R.W. Service."; document.write(quote);
この結果は次のようになります。
He read "The Cremation of Sam McGee" by R.W. Service.
文字列にバックスラッシュそのものを挿入するときはバックスラッシュをエスケープする必要があります。例えば、ある文字列に c:\temp というファイルパスを代入するときは、以下のようにします。
var home = "c:\\temp";
[編集] Unicode
Unicode は主要な文字言語の交換や表示を目指したユニバーサルな文字コードの標準です。これは南北アメリカ、ヨーロッパ、中東、アフリカ、インド、アジア、太平洋地域の言語、さらに歴史的な文字や技術記号をカバーしています。Unicode は多言語テキストの交換、処理、表示を可能にします。一般的な技術記号や数学記号も扱えます。国ごとの文字の標準の違いなど、多言語処理に関する国際化問題を解消することが期待されています。しかしながら、今のところは現代の文字と古い文字がすべてサポートされているわけではありません。
Unicode 文字セットはすべての有名なエンコーディングに使用できます。Unicode は ASCII (American Standard Code for Information Interchange) 文字セットをモデルとしています。これは各文字に対して数値と名前を割り当てています。文字エンコーディングはその文字の識別情報およびその数値(コードの位置)、さらにこの値のビット表示を指します。16 ビットの数値(コード値)は 16 進数とその頭に U を付けたもので定義されます。例えば、U+0041 は A を表します。この値に対する固有の名前は LATIN CAPITAL LETTER A です。
JavaScript 1.3 より前のバージョンでは Unicode はサポートされていません。
[編集] Unicode の ASCII や ISO との互換性
Unicode は ISO/IEC 10646-1; 1993 と完全互換です。これは ISO 10646 のサブセットです。
いくつかのエンコーディングの標準(UTF-8、UTF-16、ISO UCS-2 を含む)は Unicode を実際のビットとして物理的に表現するのに使用されます。
Unicode の UTF-8 エンコーディングは ASCII 文字と互換性があり、多くのプログラムでサポートされています。最初の 128 の Unicode 文字は ASCII 文字に対応しており、同じバイト値をとります。Unicode 文字の U+0020 から U+007E までは ASCII 文字の 0x20 から 0x7E と同等です。ASCII はラテンアルファベットをサポートしており、7 ビット文字セットを使用しますが、UTF-8 は各文字について 1 オクテットから 4 オクテットを使用します(「オクテット」は 1 バイト、すなわち 8 ビット)。これによって何百万もの文字を表現できます。別のエンコーディング標準である UTF-16 は Unicode 文字を表現するのに 2 オクテットを使用します。エスケープシーケンスによって UTF-16 は Unicode の範囲全体を 4 オクテットで表現できるようになります。ISO UCS-2 (Universal Character Set) は 2 オクテットを使用します。
JavaScript および Navigator は UTF-8/Unicode をサポートしているため、非ラテン文字、国際文字、地域化された文字そして特殊な技術記号を JavaScript プログラムで使用できます。Unicode は多言語テキストをエンコードする標準の方法を提供します。Unicode の UTF-8 エンコーディングは ASCII と互換性があるため、ASCII 文字をプログラムで使用することもきます。また、非 ASCII の Unicode 文字を JavaScript のコメント、文字列リテラル、識別子、および正規表現で使用することもできます。
[編集] Unicode エスケープシーケンス
文字列リテラル、正規表現、識別子において Unicode エスケープシーケンスを使用することができます。エスケープシーケンスは ASCII 文字 6 文字からなります。それは \u と 4 桁の 16 進数です。例えば \u00A9 は著作権記号を表しています。JavaScript ではどの Unicode エスケープシーケンスも 1 つの文字として解釈されます。
次のコードは著作権記号と "Netscape Communications" という文字列を返します。
x="\u00A9 Netscape Communications"
次の表で、よく使用される特殊文字とその Unicode 値を列挙します。
| カテゴリ | Unicode 値 | 名前 | フォーマット名 |
|---|---|---|---|
| ホワイトスペースの値 | \u0009 | タブ | <TAB> |
| \u000B | 垂直タブ | <VT> | |
| \u000C | 改ページ | <FF> | |
| \u0020 | スペース | <SP> | |
| 行終端の値 | \u000A | 改行 | <LF> |
| \u000D | 復帰 | <CR> | |
| 付加的な Unicode エスケープシーケンスの値 | \u0008 | 後退 | <BS> |
| \u0009 | 水平タブ | <HT> | |
| \u0022 | 二重引用符 | " | |
| \u0027 | 単一引用符 | ' | |
| \u005C | バックスラッシュ | \ |
表 2.2:特殊文字に対する Unicode 値
JavaScript での Unicode エスケープシーケンスの使用方法は Java のそれとは異なります。JavaScript では、エスケープシーケンスは最初から特殊文字として解釈されるということはありません。例えば、文字列中の行終端のエスケープシーケンスは、関数がそれを解釈する前にその文字列を打ち切るということはありません。どのエスケープシーケンスがコメントで使用されたとしても JavaScript はそれを無視します。Java では、1 行コメント内でエスケープシーケンスが使用された場合、それを Unicode 文字として解釈します。文字列リテラルでは Java コンパイラは最初からエスケープシーケンスを解釈します。例えば、行終端のエスケープ文字(例:\u000A)を Java で使用すると文字列リテラルを打ち切ります。また Java では行終端が文字列リテラル内では許されていないために、これはエラーが発生します。文字列リテラルで改行を表したい場合は \n を使用しなければなりません。JavaScript ではエスケープシーケンスでも \n と同じように機能します。
[編集] JavaScript ファイルにおける Unicode 文字
以前のバージョンの Gecko では、XUL から読み込まれる JavaScript ファイルは Latin-1 文字エンコーディングが前提とされていました。Gecko 1.8 からは文字エンコーディングは XUL ファイルのエンコーディングから推測されます。詳しくは XUL JavaScript における国際文字 を参照してください。
[編集] Unicode を用いた文字の表示
Unicode を用いることで異なる言語の文字や技術記号を表示させることができます。文字を適切に表示させるには、Mozilla Firefox や Netscape といったクライアントが Unicode をサポートしている必要があります。さらに適当な Unicode フォントもそのクライアントで使用できなくてはならず、またクライアントのプラットフォームが Unicode をサポートしていなければなりません。Unicode フォントが Unicode を全部は表示できないということがよくあります。Windows 95 など、Unicode を部分的にサポートしているというプラットフォームもあります。
非 ASCII 文字の入力を受け取るには、クライアントが入力を Unicode として送信する必要があります。標準的な拡張キーボードを使用すると、Unicode でサポートされている付加的な文字をクライアントが簡単には入力できなくなります。Unicode 文字を入力する唯一の方法が Unicode エスケープシーケンスを使用することという場合がたまにあります。
Unicode の詳細な情報については Unicode Home Page や The Unicode Standard, Version 2.0(出版元:Addison-Wesley、1996 年)をご覧ください。