1

問題を解決しようとしていますが、最善の解決策を見つけるのに苦労しています。(とりわけ) 次のテーブルを含むデータベースがあります。

  • 宛先リクエスト
  • サポートリクエスト
  • 交換依頼
  • 入金リクエスト

これらの各テーブルには、(エンド ユーザーから管理者まで) コメント用の列がありますが、これらすべての要求にメモを追加する機能を追加するように依頼されました。メモが追加された日時と編集者を追跡できるように、メモの各セットを別々にしたいと考えています。これは、メモをテーブルに保存し、外部キーを介してリクエストにリンクする必要があることを示唆しています。問題は、各リクエスト テーブルに、そのテーブル内で一意である自動インクリメント id 列があることですが、他のすべてのテーブルでは一意ではありません (つまり、各テーブルには ID が 200 のリクエストがある可能性があります)。

私の問題の解決策の 1 つは、リクエストの種類ごとに「Notes」テーブルを作成し、それに応じて外部キーを作成することですが、それが問題を解決する唯一の適切な方法ではありません。

私が本当に知りたいのは、id やリクエスト タイプ (基本的にはテーブル名) などを使用して外部キーを作成する有効な方法があるかどうかです。これは可能ですか?

4

2 に答える 2

3

バンドエイドとして、このようなことができます...

ここに画像の説明を入力

...次の制約がありますNote:

CHECK (
    (
        “Destination Request Id” IS NOT NULL
        AND “Support Request Id” IS NULL
        AND “Exchange Request Id” IS NULL
        AND “Deposit Request Id” IS NULL
    )
    OR (
        “Destination Request Id” IS NULL
        AND “Support Request Id” IS NOT NULL
        AND “Exchange Request Id” IS NULL
        AND “Deposit Request Id” IS NULL
    )
    OR (
        “Destination Request Id” IS NULL
        AND “Support Request Id” IS NULL
        AND “Exchange Request Id” IS NOT NULL
        AND “Deposit Request Id” IS NULL
    )
    OR (
        “Destination Request Id” IS NULL
        AND “Support Request Id” IS NULL
        AND “Exchange Request Id” IS NULL
        AND “Deposit Request Id” IS NOT NULL
    )
)

このように、既存のテーブルの PK を変更する必要はありません (モデルの残りの部分とクライアント アプリケーションに連鎖的な影響を与える可能性があります)。ただし、Notesテーブルを「繰り返す」ことなく、適切な参照整合性を維持できます。

于 2012-05-21T23:04:58.847 に答える
1

object_id が要求テーブルのいずれかを参照するテーブル Note( object_id, note ) を持つことができます。データベースに外部キー制約を設定する必要はありません。または、制約を本当に維持したい場合は、制約句を使用できます (ベンダー固有の可能性がありますか?)。

Note が関連付けられているリクエスト テーブルを特定するには、Note に列挙型の値を設定します。一部のデータベース ベンダーには Enum 型があり、他のベンダーは Int のみを使用する場合があります。request_type enum(DESTINATION、SUPPORTなど)のような列になります。

データベースが小さい場合、またはしばらくオフラインにすることができる場合は、代わりに、4 つの object_id すべてを生成する単一のシーケンスを使用するようにテーブルを再作成することができます。そのようにして、ID は異なる要求テーブル全体で一意になります。この種の状況では、普遍的に一意の object_id シーケンスを使用するのが好きです。

一部のベンダー (postgres) では、テーブル継承を使用できます。テーブルの継承では、create table destination_request(....) inherits(note); のようなことを行います。これにより、note テーブル内のすべてのフィールドが、destination_request テーブルに対するクエリで使用できるようになります。これはある意味で機能し、舞台裏で作業を行います。概念的には、リクエストは注目すべきサブタイプではないため、これは OO 設計の観点からは理想的ではなく、テーブルの継承は他のデータベース ベンダーに移植できない可能性があります。ここでの純度にどの程度関心があるかは、あなた次第です。

上で提案したように、各テーブルを指す 4 つの異なる外部キーを持つことができますが、ほとんどが Null 値のテーブルが残ります...おそらく、多くの null 値を持つテーブルを持つよりも、4 つの異なるノート テーブルを持つ方がよいでしょう。

于 2012-05-21T23:45:33.867 に答える