選択型をテーブルにマッピングする手法
選択型を 1 レベルの 継承 階層と捉えると、オブジェクト階層を RDB のモデルにマッピングするアプローチを利用できる オブジェクト階層を RDB のモデルにマッピングするアプローチ
この中でも特に有効なのは以下の 2 つ
選択型のサンプル
code:fsharp
type Contact =
{ ContactId: ContactId
Info: ContactInfo }
and ContactInfo =
| Email of EmailAddress
| Phone of PhoneNumber
and EmailAddress = EmailAddress of string
and PhoneNumber = PhoneNumber of string
and ContactId = ContactId of int
1. すべてのケースを同じテーブルに格納する
code:sql
CREATE TABLE ContactInfo (
ContactId int NOT NULL,
IsEmail bit NOT NULL,
IsPhone bit NOT NULL,
EmailAddress NVARCHAR(100),
PhoneNumber NVARCHAR(25),
CONSTRAINT PK_ContactInfo PRIMARY KEY (ContactId)
)
どのケースが使われているかを示すフラグが必要
一部のケースでのみ使われるカラムは、NULL 許容
2. 各ケースをそれぞれのテーブルに格納する
code:sql
CREATE TABLE ContactInfo (
ContactId int NOT NULL,
IsEmail bit NOT NULL,
IsPhone bit NOT NULL,
CONSTRAINT PK_ContactInfo PRIMARY KEY (ContactId)
)
CREATE TABLE ContactEmail (
ContactId int NOT NULL,
EmailAddress NVARCHAR(100) NOT NULL,
CONSTRAINT PK_ContactEmail PRIMARY KEY (ContactId)
)
CREATE TABLE ContactPhone (
ContactId int NOT NULL,
PhoneNumber NVARCHAR(25) NOT NULL,
CONSTRAINT PK_ContactPhone PRIMARY KEY (ContactId)
)
メインテーブルとケースごとに子テーブルを作成し、主キーは同じ値を共有する
メインテーブル: アクティブなケースを示す ID や フラグを管理する
子テーブル: 各ケースのデータを管理する
テーブル数が増えるが、より適切な制約(NOT NULL)が可能に
どちらを選択するか?
基本的には「1. すべてのケースを同じテーブルに格納する」で管理し、共通点が少ない場合のみ「2. 各ケースをそれぞれのテーブルに格納する」を選択すると良い