24. JavaScript の字句解析 — 識別子と予約語、数値、文字列、コメント
JavaScript のは CSS と同じ「先頭の文字で種類を決めて読む」形です。 §12 の字句文法のうち、この実装が扱うのは、区切り記号(+ - = ( ) { } ; . ,)、数値、文字列(" と ' の 2 種類と \n などのエスケープ)、、(var let const function return)、// の行コメントです。
識別子と予約語の区別は、読み終わってから決めます。英字・_・$ で始まる文字の並びを識別子として読み、それが KEYWORDS の一覧(var / let / const / function / return)にあれば Keyword、なければ Identifier にします。だから や は Identifier、function は Keyword です。本物の予約語は 30 以上ありますが、で使うものだけに絞ってあります。
数値は数字と . の並びを f64 にします(JavaScript の数は倍精度浮動小数点)。文字列は開き引用符と同じ引用符が来るまでで、\ の次の 1 文字をエスケープとして処理します。2 文字の演算子(=== や +=)、正規表現リテラル、テンプレートリテラル、/* */ のコメントは扱いません。知らない記号は Punctuator としてそのまま流し、弾くのは構文解析に任せます(CSS と同じ分担)。
下のコードを実行すると、5 つの入力の列が出ます。document.getElementById("title") が Identifier、Punctuator('.')、Identifier、Punctuator('(')、Str、Punctuator(')') の 6 トークンになるところを見てください。メソッド呼び出しという単位は字句解析にはありません。
本物のブラウザでは: の字句解析器 src/parsing/scanner.cc は、入力を Utf16CharacterStream で UTF-16 の列として見て、「JavaScript で曖昧な最長の列は 4 文字なのでは最大 4 文字」で次の走査関数を選びます。識別子の判定は 128 文字の表で 1 分岐、予約語は gperf の完全ハッシュで長さと先頭 2 文字から引きます(v8.dev/blog/scanner)。この回の で 1 文字先読みし、文字列の表で予約語を見る形は、その素朴版です。 は js/src/frontend/TokenStream.h です。
開発のどこに活かすか: 「識別子として読んでから予約語か調べる」は、どの言語の字句解析でも同じ手順で、自前の DSL(検索条件式、権限ルール、ワークフロー定義)を作るときにそのまま使えます。また、JavaScript の数が全部 f64 であること(0.1 + 0.2 の誤差、2^53 を超える整数の丸め)が、字句解析の段階で決まっていることも分かります。
点線の付いた語はタップすると説明が出ます。用語集を開く →
▶ サンプルコードを実行してみよう(自由に書き換えてOK)
手元で動かす(配布物)
図やコードに出てくる用語(タップで説明)
学んだ概念を、素朴な例から実務寄りの例まで3つの具体例で確認します。
公式ドキュメントで詳しく ↗