オブジェクト
Object
オブジェクトは、関連するデータや振る舞いをまとめて扱う値・実体です。言語によって仕組みは異なります。JavaScriptではクラスから作るほか、オブジェクトリテラルでも作成でき、必ずメソッドを持つ必要はありません。
🐾 猫で例えると?
並んで香箱座りをする茶トラとアメショ。彼らは「猫」という共通の設計図(クラス)から生み出されましたが、「雷が鳴ると隠れる甘えん坊」と「おやつの気配に敏感なツンデレ」という、それぞれ全く異なる属性(データ)と振る舞い(処理)を持つ、紛れもない具体的な「実体」です。このプログラム上で実際に活動している個体がオブジェクトです。
💻 開発現場における「オブジェクト」とは?
オブジェクト指向プログラミングにおいて、システムは「オブジェクト同士の相互作用」として設計されます。例えばECサイトなら、「ユーザー」オブジェクトが「商品」オブジェクトを「カート」オブジェクトに入れる、といった具合です。データ(状態)と処理(振る舞い)を一つのオブジェクトにまとめることで、関連するコードがシステム全体に散らばるのを防ぎ、人間にとって直感的で管理しやすい構造を作ることができます。
なお、JavaScriptのようなプロトタイプベースの言語では、クラスから生成されたインスタンス(実体)だけでなく、キーと値のペアの集合体そのものをシンプルに「オブジェクト」と呼ぶことも多く、文脈によって指すニュアンスが少し異なる場合があります。
⚠️ オブジェクトの仕組みと注意点
JavaScriptでは、オブジェクトを変数へ代入すると、同じオブジェクトを指す値が共有されます。関数の引数も値として渡されるため、厳密には「参照渡しで呼び出し元の変数そのものを変更する」仕組みとは違います。プロパティの変更と、変数への再代入を分けて考えましょう。
const catA = { name: "アメショ", details: { mood: "のんびり" } };
const catB = catA; // 同じオブジェクトを指す
catB.name = "茶トラ";
console.log(catA.name); // 茶トラ
const catC = { ...catA }; // 浅いコピー
catC.name = "三毛";
console.log(catA.name); // 茶トラのまま
console.log(catC.details === catA.details); // true:内側は共有 同じオブジェクトを複数から更新する設計では、誰が変更するかを明確にします。上の浅いコピーは外側だけを作り直すため、入れ子のdetailsの変更は元にも見えます。コピーの深さを確認することが大切です。
🛠️ オブジェクトを賢く使うためのポイント
複雑なシステムを安定して稼働させるためには、オブジェクトの特性を正しく理解して扱う必要があります。
- 複製できるものを確認: structuredCloneは対応する値の深いコピーに使えますが、関数など対象外もあります。JSON化して戻す方法も型やundefinedなどを保持しないため、万能な複製として使わないようにします。
- 状態をむやみに変えない(不変性): オブジェクトのプロパティを外部から直接書き換えるのではなく、新しくオブジェクトを生成し直す設計(イミュータブルな設計)が現代の開発では好まれます。
- 巨大な「神オブジェクト」を作らない: 何でもできる巨大なオブジェクトは保守が困難になります。一つのオブジェクトには一つの責任を持たせる(単一責任の原則)ことが重要です。
個性の違う茶トラとアメショのように、オブジェクトは状態と、それを扱う処理をまとめて捉えるための考え方です。設計では、どの情報を持ち、どの操作に責任を持つかを決めると、役割が重なりすぎた部品を見直しやすくなります。