最初のものは、わずかに不完全な場合でも、より正規化されています。採用できるアプローチはいくつかあります。最も単純な(厳密に言えば、最も「正しい」)には、明らかなFK制約のある2つのテーブルが必要です。
commentid ---- subjectid ----- idType
--------------------------------------
1 22 post
2 26 photo
3 84 reply
4 36 post
5 22 status
idType
------
post
photo
reply
status
必要に応じて、char(1)などを使用して、キー/インデックスの長さに対するvarcharの影響を減らすか、ORMを使用する場合はORMでの使用を容易にすることができます。 NULLは常に煩わしいものであり、デザインにNULLが現れるのを見始めたら、それらを排除する便利な方法を見つけられれば、より良い結果が得られます。
2番目のアプローチは、1億行を超える行を処理するときに私が好むアプローチです。
commentid ---- subjectid
------------------------
1 22
2 26
3 84
4 36
5 22
postIds ---- subjectid
----------------------
1 22
4 36
photoIds ---- subjectid
-----------------------
2 26
replyIds ---- subjectid
-----------------------
3 84
statusIds ---- subjectid
------------------------
5 22
もちろん、(わずかに非正規化された)ハイブリッドアプローチもあります。これは、ダーティになる傾向があるため、大規模なデータセットで広く使用しています。事前定義されたidTypeの特殊化テーブルを提供するだけですが、commentIdテーブルにはアドホックなidType列を保持します。
ハイブリッドアプローチでさえ、非正規化されたテーブルの2倍のスペースしか必要としないことに注意してください。 idTypeによる簡単なクエリ制限を提供します。ただし、整合性制約は単純ではなく、タイプテーブルの派生UNIONに対するFK制約です。私の一般的なアプローチは、ハイブリッドテーブル、または同等の更新可能なビューのいずれかでトリガーを使用して、正しいサブタイプテーブルへの更新を伝播することです。
単純なアプローチとより複雑なサブタイプのテーブルアプローチの両方が機能します。それでも、ほとんどの目的でKISSが適用されるので、おそらくID_TYPESテーブルと関連するFKを導入して、それで済ませるべきだと思います。