エンティティと値オブジェクトの特性を識別する

エンティティと値オブジェクトの特性を識別する

[[411622]]

正確さは集計の設計に直接影響するため、エンティティと値オブジェクトを区別することは非常に重要です。

集約は境界である

DDD では、集約はエンティティと値オブジェクト間の境界です。集約は完全なドメイン概念を外部的に表現し、オブジェクト指向設計の基本原則に従います。集約は多くの場合、複数の小さく凝集度の高いドメイン概念で構成されます。集約内のドメイン モデルはツリーを形成します。ツリーのルートはエンティティである必要があり、集約ルート (Aggregate Root) と呼ぶことができます。もちろん、集約の唯一の入口または出口であるルート エンティティ (Root Entity) と呼ぶこともできます。たとえば、Order 集約は、Order 集約の唯一の代表である Order ルート エンティティを定義します。

境界付けられたコンテキストのすべてのドメイン モデル (エンティティと値オブジェクト) は、草原の部族がパオの緩やかなコミュニティで構成されているのと同じように、関係の強さと概念の完全性に応じて複数の集約に分割されます。

値オブジェクトとエンティティの違いを考慮すると、それらのライフサイクルを管理する必要がある場合、値オブジェクトは集約の境界から独立して存在することはできません。つまり、ドメイン モデルの集約を識別する場合、エンティティと値オブジェクト間の関係の強さは集約境界の定義に影響しません。エンティティと値オブジェクトの間に関係がある限り、その関係がどれほど強いかに関係なく、値オブジェクトは、関係が存在するエンティティと同じ集約に配置する必要があります。値オブジェクトが複数のエンティティと関係を持っている場合、複数のエンティティが 1 つの集約に属していることを意味します。または、次の図に示すように、値オブジェクトを複数のコピーにコピーして、異なる集約に配置する必要があることを意味します。

このように、集約境界の識別は、エンティティ関係の強さの判断になります。エンティティと値オブジェクトを正しく識別する限り、集約を識別するときに値オブジェクトを考慮する必要がなくなり、識別の難易度が軽減されます。

文脈の影響

エンティティと値オブジェクトの本質的な違いは、それらが固有の ID を持っているかどうかにあることはわかっていますが、多くの場合、この違いは依然としてもっともらしいようです。さらに、エンティティと値オブジェクトの定義は絶対的なものではありません。異なるコンテキストでは、同じドメイン概念が異なる設計タイプとして定義される場合があります。たとえば、以下の紙幣:

購入の文脈では、買い手と売り手は紙幣の額面と通貨の種類だけを気にします。価値が等しい限り、それらは同じオブジェクトとみなすことができるため、値オブジェクトとして定義する必要があります。お金を印刷する文脈では、各紙幣には一意の識別子があります。たとえ両方とも人民元で100元であっても、IDが異なっている限り、それらは異なるオブジェクトとみなされるため、エンティティとして定義されます。したがって、エンティティと値オブジェクトを正しく区別するには、特定のコンテキストが必要です。

特定された特徴

それでも、比較的客観的な判断基準がまだ欠けている。そのために、私は以下の特徴をまとめました。

平等

エンティティと値オブジェクトを区別するには、まず等価性によって判断します。ドメイン モデル オブジェクトの属性値が等しい限り、それらは同じオブジェクトとみなされ、最初に値オブジェクトとしてモデル化する必要があります。それ以外の場合は、ドメイン モデル オブジェクトの一意の識別子を定義し、それをエンティティとしてモデル化する必要があります。

注: 等価性チェックを実行する場合、一意の識別子として使用される ID はドメイン モデルの属性とは見なされません。

たとえば、住所ドメインの概念では、国、州、都市、通り、郵便番号の属性値が等しい限り、それらは同じ住所とみなすことができ、Address クラスは値オブジェクトとして定義する必要があります。注文ドメインというおなじみの概念では、理論上は注文番号を除いて同じ属性を持つ 2 つの異なる注文が存在する可能性があるため、一意の注文番号を割り当てる必要があることは明らかです。注文はエンティティとして定義する必要があります。

ただし、同等性を判断する場合、ID と属性の間に暗黙的な対応関係がある場合があります。たとえば、出版業界の正式な出版物である書籍には、書籍フィールドの概念の ID に相当する一意の ISBN 番号があるため、Book はエンティティとして定義する必要があります。 Bookの等価性を判断する際に、ISBNを使って等価性を判断する必要はありません。基本的には、書籍名、著者(翻訳者)、出版社、価格、発行日、版、ページ数、単語数などの属性値が同じであれば、同じ書籍とみなすことができます。ということは、Bookを値オブジェクトとして定義できるということでしょうか。

当然のことながら、同等性の判断を行う際に考慮する属性が増えるほど、より多くの属性の組み合わせが出現し、「隠れた」一意の識別機能を形成します。ビジネス ルールを反映する一部の ID は、それ自体が属性値に基づいて定義されます。たとえば、航空会社の 2 文字コード、フライト番号、離着陸空港の 3 文字コード、およびフライトの日付に基づいて、フライトの一意の識別子を決定できます。一意の識別子を使用して同じフライトであるかどうかを判断でき、マッピングされた複数の属性値に基づいて同等性を判断することもできます。これにより、エンティティと値オブジェクトを区別する際に、人々が躊躇するように見えることがあります。たとえば、Tencent Conference の会議番号は会議の ID です。会議の平等性を比較する場合、会議番号以外の属性、たとえば会議名、会議の種類、開始時間、終了時間、作成者、作成時間などを考慮すると、会議の平等性を判断できますか?

したがって、平等性の判断に加えて、不変性も考慮する必要があります。

不変性

Eric Evans は、値によって等しいと判断される値オブジェクトは不変であるべきであるため、値オブジェクトを不変クラスとして定義することを提案しました。引き続き購入の文脈における紙幣の例を取り上げますと、50 元 + 50 元 = 100 元です。この 100 元は元の 50 元とは異なる紙幣です。

逆に、ID を除いて、オブジェクトの他のすべての属性値は、新しいオブジェクトを作成せずに変更できます。この場合、ドメイン オブジェクトは変更可能と見なされ、エンティティとして定義されていると見なされます。前述の通り、Meeting オブジェクトについては、meetingId 値が変更されない限り、会議名、会議タイプ、開始時刻、終了時刻などの属性値が大幅に変更された場合でも、同じ会議であるとみなします。明らかに、会議はエンティティとして定義する必要があります。

典型的な注文集約を考えてみましょう。

注文集計で OrderItem をエンティティとして定義するのはなぜでしょうか? ID 属性を無視すると、orderId、product、quantity の値が同じであれば、同じ注文項目とみなすことができます。ただし、注文品目の数量値は変更可能であり、数量が変更された注文品目は別の注文品目とはみなされません。注文項目は可変であるため、エンティティとして定義する必要があります。

OrderItem の Product プロパティを値オブジェクトとして定義する必要があるのはなぜでしょうか。Product 型は productId プロパティも定義していることを知っておく必要があります。これは ID 識別子を持っているため、エンティティとして定義すべきではないでしょうか。注文コンテキストでは、製品の productId は製品コンテキストの製品 ID から取得されるためです。注文集計では、productId は Product クラスの属性値と見なすことができます。 productId、name、price の値が同じであれば、同じ製品とみなされ、値は変更されません。これが、Product が値オブジェクトとして定義される理由です。

独立

平等性と不変性を考慮した後でも、独立性という例外が 1 つあります。エンティティの属性として、値オブジェクトはエンティティに添付される必要があり、独立して存在することはできません。ドメイン オブジェクトが等価性と不変性の両方を満たす場合は、値オブジェクトとして定義できます。ただし、独立して存在し、そのライフ サイクルを管理する必要がある場合は、そのようなクラスをエンティティに「アップグレード」する必要があります。

出席の文脈で休暇ドメインの概念を検討します。中国の太陰暦の休日のため、毎年新しい休日を設定する必要があります。休日の概念に対応する Holiday クラスは次のように定義されます。

当然ですが、このクラスの属性値がすべて等しい場合は、同じ休日とみなすことができます。休日の値が変更されると、別の休日とみなすこともできます。つまり、Holiday クラスは等価性と不変性の両方を満たしており、値オブジェクトとして定義する必要があります。ただし、出席コンテキストのドメイン モデルでは、Holiday クラスは完全に独立しており、他のエンティティに接続されておらず、ライフ サイクルも管理する必要があります。このとき、独立性の特性に従い、エンティティに「アップグレード」する必要があります。

優先度

上記の 3 つの特性は重要度順に並べられているわけではなく、総合的に考慮する必要があります。それでも判断できない場合は、優先順位の原則に従ってください。つまり、ドメイン概念を値オブジェクトとしてモデリングすることを優先します。

<<:  ドローンが農家にもたらす3つのメリット

>>:  再帰アルゴリズム: 不可解なスイッチ「ライトを引く」

ブログ    
ブログ    
ブログ    

推薦する

AIの次の目的地:洗練された生活シナリオのインテリジェント時代

[[348783]] Canvaからの画像テクノロジーは生活の中でどのような役割を果たしているのでし...

60年ぶり! AI が新しい抗生物質の最初のバッチを発見し、MIT の主要な研究が Nature に掲載されました。人類はスーパーバグとの戦いに希望を持っている

60年間、人類は抗生物質の研究において大きな進歩を遂げていません。しかし、このギャップはAIによって...

大学入試結果が続々発表。ボランティア応募で人工知能が注目の選択肢に

今日から、全国各地の大学入試結果が続々と発表され、出願手続きが始まります。今年、各大学は、専門分野、...

Python データマイニングと機械学習入門

データマイニングとは何ですか?機械学習とは何ですか?Python データの前処理を実行するにはどうす...

「人工知能+教育」はどのような機会と課題をもたらすのでしょうか?

人工知能がどのような新しい形で登場するかが話題になっている一方で、教育分野では新たな一連の変化が起こ...

ケビン・ケリーがAIブームを解説:超人的なAIを暴く5つの神話

人工知能は非常に人気が高まっているため、ニュースで報道される超知能に関する予測が実現可能なものなのか...

将来、人工知能に最も影響を受ける5つの業界!

人工知能の概念はますます普及しています。急速に発展する人工知能にとって、チェスの世界を席巻することは...

AI人材の確保をめぐる秘密の戦い:中国が勝利する可能性は?

[[251811]]画像ソース @Visual China人工知能の概念は、提唱されてから60年以...

...

機械学習でよく使われる7つの線形次元削減手法の概要

前回の記事では主に非線形次元削減手法についてまとめました。この記事では、一般的な線形次元削減手法につ...

無意味または有害なボットトラフィックは年間最大2億5000万ドルのコストがかかる

Cyber​​news によると、ますます多くの企業が、検出がますます困難になっている悪意のあるボッ...

...

スマートセンサー: 従業員をオフィスに戻すための鍵となるか?

新型コロナウイルス感染症のパンデミックにより、多くの人々の働き方が変化しました。現在、多くの企業は、...