esspec

第96回 ECMAScript仕様輪読会 記録

本セッションでは、前回に引き続き「21.4 Date Objects」の仕様を確認しました。主に Date.UTC 関数から Date.prototype の各メソッド(Getter/Setter、文字列変換)について、仕様のアルゴリズムと実際の挙動をコードで検証しながら読み進めました。

1. 前回の振り返り

前回確認した以下の内容を軽く復習しました。


2. Date.UTC ( year [ , month [ , date [ , hours [ , minutes [ , seconds [ , ms ] ] ] ] ] ] )

Date.UTC は、引数をUTCとして解釈し、対応するタイムバリュー(数値)を返します。

アルゴリズムのポイント

  1. 各引数に対して ToNumber を適用する。
  2. デフォルト値の適用:
    • month がなければ 0
    • date がなければ 1(Dateのみ1オリジン)。
    • 時・分・秒・ミリ秒がなければ 0
  3. MakeFullYear, MakeDay, MakeTime, MakeDate という内部操作を経て値を生成する。
  4. TimeClip: 生成された値がDateオブジェクトで表現可能な範囲(約±285,426年)に収まっているかを確認し、範囲外なら NaN を返す。

Dateコンストラクタとの違い

// 検証:範囲外の年は NaN になる
Date.UTC(275760, 8, 13); // 数値が返る
Date.UTC(285427, 0, 1);  // NaN (TimeClipによる)

3. Date.prototype オブジェクト

Date.prototype 自体の特性について確認しました。


4. Date.prototype の Getter メソッド

各Getter(getDate, getHours, getTime など)の共通アルゴリズムを確認しました。

基本的な流れ

  1. thisDate オブジェクトとして受け取る。
  2. this[[DateValue]] 内部スロットを持っているかチェック(RequireInternalSlot)。なければ TypeError
  3. 内部スロットの値を t とする。
  4. tNaN なら NaN を返す。
  5. それ以外なら、LocalTime(t) (ローカルタイムへの変換)を適用した上で、必要な要素(日、時など)を抽出して返す。

Date.prototype.getTime()

内部スロット [[DateValue]] の値をそのまま返す(変換なし)。

Date.prototype.getTimezoneOffset()

UTCとローカルタイムの差分を「分」で返します。

// 検証
new Date().getTimezoneOffset(); // 日本なら -540

5. Date.prototype の Setter メソッド

各Setter(setDate, setFullYear, setTime など)の挙動を確認しました。

Date.prototype.setDate ( date )

特定の「日」を設定します。

const d = new Date(2026, 0, 1); // 2026-01-01
d.setDate(32); // 2026-02-01 になる
d.setDate(0);  // 2026-01-31 になる(2月の0日=1月の最終日)

Date.prototype.setFullYear ( year [ , month [ , date ] ] )

年を設定するメソッドですが、オプションで月と日も同時に設定可能です。

Date.prototype.setTime ( time )

内部スロット [[DateValue]] を直接書き換えます。


6. 文字列変換メソッド

Date.prototype.toDateString ()

日付部分のみを人間が読める形式の文字列で返します(例: “Sun Mar 01 2026”)。

Date.prototype.toISOString ()

ISO 8601形式の文字列を返します。

Date.prototype.toJSON ( key )

JSON.stringify で呼ばれるためのメソッドです。

  1. this をオブジェクトに変換する。
  2. ToPrimitive をヒント「Number」で呼び出す。
  3. その結果が有限の数値でない(NaNInfinity)場合は null を返す。
  4. そうでなければ、自身の toISOString() メソッドを呼び出した結果を返す。

特徴:

// 検証:ジェネリックな挙動
const obj = {
  toISOString: () => "Custom ISO String",
  toJSON: Date.prototype.toJSON
};
console.log(obj.toJSON()); // "Custom ISO String"

// 数値として不正な場合は null
const invalidDate = new Date(NaN);
console.log(invalidDate.toJSON()); // null

次回の予定

次回のセッションでは、Date.prototype.toLocaleDateString から読み進める予定です。