質問

次の例を見てみたいと思います。

  • これが適切な場合
  • これが適切でない場合

データベースの選択によって上記の例に違いが生じることがありますか?

役に立ちましたか?

解決

これは本当に次のような質問のようです 代理 キーは常に自動インクリメントする数値または GUID であるため、単一の列になります。 自然 キーを真に一意にするためには、多くの場合、複数の情報が必要です。1 列のみの自然キーを取得できる場合は、いずれにしても、その点は明らかに意味がありません。

どちらか一方のみを使用することを主張する人もいます。実稼働データベースの作業に十分な時間を費やすと、コンテキストに依存しないベスト プラクティスがないことがわかります。

これらの回答の中には SQL Server の用語を使用しているものもありますが、その概念は一般的にすべての DBMS 製品に適用できます。


単一列の代理キーを使用する理由:

  • クラスター化インデックス。 クラスター化インデックスは、データベースが単に追加できる場合に常に最高のパフォーマンスを発揮します。それ以外の場合は、DB が追加する必要があります。 ページ分割. 。これはキーが次の場合にのみ適用されることに注意してください。 一連, 、つまり自動インクリメント シーケンスまたはシーケンシャル GUID のいずれか。任意の GUID を使用すると、パフォーマンスが大幅に低下する可能性があります。

  • 関係。 文字タイプやその他の非コンパクトなデータを含めて、キーの長さが 3、4、5 列の場合、結果的に無駄になります。 巨大な 他の 20 個のテーブルにこのキーへの外部キー リレーションシップを作成する必要がある場合、スペースの量が増加し、パフォーマンスが低下します。

  • ユニークさ。 そうしない場合もあります 持っている まさに自然な鍵です。おそらくテーブルはある種のログであり、同時に 2 つの同じイベントを取得する可能性があります。あるいは、あなたの本当のキーは、唯一決定できる具体化されたパスのようなものかもしれません 行はすでに挿入されています。いずれにせよ、クラスター化インデックスや主キーは常に一意である必要があるため、他に真に一意の情報がない場合は、代理キーを使用する以外に選択肢はありません。

  • 互換性。 ほとんどの人はこれに対処する必要はありませんが、自然キーに次のようなものが含まれている場合は、 hierarchyid, 、一部のシステムでは読み取れない可能性もあります。この場合、またあなたは、 しなければならない これらのアプリケーションで使用するための単純な自動生成代理キーを作成します。たとえ自然キーに「奇妙な」データがなかったとしても、一部の DB ライブラリでは複数列の主キーの処理に多くの困難を抱えていますが、この問題はすぐに解消されつつあります。

複数列の自然キーを使用する理由

  • ストレージ。 データベースを扱う人の多くは、この要素を考慮する必要があるほど大規模なデータベースを扱うことはありません。しかし、テーブルに数十億または数兆の行がある場合、このテーブルには可能な限り絶対最小限のデータを保持する必要があります。

  • レプリケーション。 はい、GUID または連続した GUID を使用できます。ただし、GUID には独自のトレードオフがあり、何らかの理由で GUID を使用できない、または使用したくない場合は、レプリケーション シナリオでは複数列の自然キーの方がはるかに優れた選択肢となります。 本質的に世界的にユニークな - つまり、それを一意にするために特別なアルゴリズムは必要ありません、それは一意です 定義により. 。これにより、分散アーキテクチャについての推論が非常に簡単になります。

  • パフォーマンスの挿入/更新. 。代理キーは無料ではありません。一意の列のセットがある場合 そして これらの列は頻繁にクエリされるため、これらの列をカバーするインデックスを作成する必要があります。インデックスは最終的にテーブルとほぼ同じ大きさになり、スペースを無駄にします。 そして 変更を加えるたびに 2 番目のインデックスを更新する必要があります。もしあなたがただそれを手に入れることができるとしたら、 1つ テーブルのインデックス (クラスター化インデックス) を実行する必要があります。


それがすぐに思い浮かぶことです。また何か急に思い出したら更新します。

他のヒント

(少なくともアプリケーション開発者の観点からは) ほとんどの場合、主キーを自動生成キーにし、複数の列に UNIQUE 制約とインデックスを作成する方が良いと思います。

  • 自動生成された 1 つの主キーを使用すると、他のテーブルからこのテーブルへの参照を簡単に追加できます。
  • 自動生成された主キーは、ORM ライブラリでより簡単に機能します。
  • また、将来一意性制約が変更された場合でも、既存の主キーを変更する必要はありません。

DBA は複数列の主キーが常にあれば十分であると考えていたため、私はいくつかの頭痛の種となる状況に遭遇しましたが、将来の要件の変更によってこれが誤りであることが判明しました。

ほぼ常に主キーが必要になるため、既存の 2 つの列を主キーとして選択するか、新しい自動インクリメント PK を作成して代わりに 2 つの列に通常の一意の制約を設定するかの選択になると思います。

2列の主キーが必要な場合:

  • 他の 2 つのテーブルを参照する中間テーブルがあり、それが 2 つの外部キーのみで構成されているとします。多対多の関係の場合、主キーにするためだけに列を追加しても意味がありません。すでに持っている 2 つの列を主キーとして使用します。

自動インクリメント主キーが必要な場合:

  • 別のテーブルからテーブルを参照する場合、参照先テーブルの主キーのデータが外部キーとして繰り返されるため、ターゲット テーブルの主キーを小さくする必要があります。また、比較を迅速に行うことも必要です。
  • テーブルに追加するすべてのインデックスには、クラスタリング キー (通常は主キーと同じ) のコピーが含まれます。クラスタリング キーが必要以上に大きい場合、そのテーブルのすべてのインデックスも必要以上に大きくなります。

いくつかの例...

適切な:

  • ほとんどの状況で多対多の関係を実装する場合の OLTP システム。

不適切:

  • OLAP システムのディメンション テーブルの場合 -- ファクト テーブルをできるだけ小さく (そして高速に) できるように、ディメンション キーをできるだけ小さくする必要があります。

  • 組み合わせが一意であるかどうかわからない場合に使用します。これはかなりひどい例であることは確かですが、「人物」テーブルは複数列の PK には不適切な選択です。

あなたが別のテーブルを接続する外部キーフィールドを持つリンクテーブルを持っている場合、

それが適切だときの一例である。

一般的に、それはおそらく可能な場合は、あなたの主キーとしてフィールドを識別し、既存の使用することをお勧めします。あなたは自然のidフィールドを持っていない、とあなたはユニークなPKを得るために多くの分野を結合しなければならない場合は、自動番号を使用することはおそらく良いでしょう。以上の2つのフィールドを持つ主キーは厄介取得することができます。

私たちは、マルチコラムindexsとキーを使用し、当社のアプリケーションで優れたパフォーマンスの向上を発見しました。それは、私たちは私たちの最も一般的なクエリにインデックスを作成することができ、全体のselect句は、インデックスに可能性があるため、メインテーブルにもアクセスされませんでした。しかし、それはあなたのアプリケーションやデータセットに依存します。

時には複合自然キーは、直感的な意味をなします。例えば。列の企業のいくつかの詳細を(PKがComapnyIdである)あなたが会社のためのテーブルがあるとします。また、その歴史thoughout会社の最高経営責任者(CEO)の名前を格納するための要件を持っています。自然の不変のは一つの会社が一度に一つだけ最高経営責任者(CEO)を持つことができるということです。たCompanyIdの複合PK(会社テーブルのたCompanyIdにFK)+ FROMDATEでCompanyCeoテーブルを作成するために、そして直感的です。そのテーブルの他の列はのToDateとCeoNameかもしれません。この方法は、あなたが、唯一の最高経営責任者(CEO)は、特定の日に始めることができることを保証することができます。

ライセンス: CC-BY-SA帰属
所属していません StackOverflow
scroll top