Mehrspaltige Primärschlüssel?

7

Zum Beispiel habe ich 2 Tabellen, Users und UserRelations , und es ist eine Eins-zu-viele-Beziehung.

Für die Tabelle UserRelations kann ich eine Identitätsspalte haben und sie zum Primärschlüssel machen:

%Vor%

Oder ich kann die Tabelle wie folgt gestalten:

%Vor%

und make UserID + TargetID den Primärschlüssel.

Meine Frage ist, was bedeutet das für jedes Design, was besser für die Leistung ist?

    
Ray Fan 08.12.2008, 21:21
quelle

11 Antworten

9

Wenn Sie das frühere Design mit der Spalte "Überflüssige Identität" verwenden, gibt es keine Einschränkung für das Einfügen von zwei Zeilen mit identischer Benutzer-ID und Ziel-ID. Sie müssten eine UNIQUE -Einschränkung für die anderen beiden Spalten erstellen, die sowieso einen zusammengesetzten Index erstellt.

Auf der anderen Seite bestehen einige Frameworks (z. B. Rails) darauf, dass jede Tabelle einen Ersatzschlüssel namens id hat, so dass das "richtige" Design möglicherweise nicht funktioniert. Es hängt davon ab, welchen Code Sie schreiben, um dieses Tabellendesign zu verwenden.

    
Bill Karwin 08.12.2008, 21:28
quelle
7

Das ist fast ein religiöses Thema. Für jede Person, die sagt, dass sie einen nicht-intelligenten Ersatzschlüssel benutzt, weist jemand darauf hin, dass Ersatzschlüssel überflüssig sind, usw., etc. Tun Sie alles, was sich für Sie und Ihr Team am wohlsten fühlt.

Wenn Sie sich dafür entscheiden, einen Ersatzschlüssel zu verwenden, sollten Sie dem natürlichen (in diesem Fall mehrspaltigen) Schlüssel eine eindeutige Einschränkung auferlegen, um die Integrität Ihrer Daten zu erhalten.

Ich wähle normalerweise einen zusätzlichen Ersatzschlüssel, da es einige wünschenswerte (nicht notwendigerweise erforderliche) Primärschlüsseleigenschaften gibt, die natürliche Schlüssel manchmal nicht haben:

  • Eindeutige Werte: Der Primärschlüssel muss jede Zeile in einer Tabelle eindeutig identifizieren.
  • Nicht intelligent: Der Primärschlüssel sollte vorzugsweise keine eingebettete semantische Bedeutung haben. Mit anderen Worten, es sollte keine Eigenschaften der Entität beschreiben. Eine Kunden-ID von 12345 wird normalerweise gegenüber RoadWarrior bevorzugt.
  • Keine Änderung im Laufe der Zeit: Der Wert eines Primärschlüssels sollte sich normalerweise nicht ändern. Wenn Sie einen Primärschlüsselwert ändern, ändern Sie die Identität einer Entität, was normalerweise keinen Sinn ergibt. Ich bevorzuge nicht-intelligente Schlüssel, weil sie sich weniger ändern.
  • Single-Attribut: Ein Primärschlüssel sollte die Mindestanzahl von möglichen Attributen haben. Primärschlüssel mit einem einzelnen Attribut sind wünschenswert, weil sie für Anwendungen einfacher zu handhaben sind und die Implementierung von Fremdschlüsseln vereinfachen.
  • Numerisch: Es ist oft einfacher, eindeutige Werte zu verwalten, wenn sie numerisch sind. Die meisten Datenbanksysteme haben interne Routinen, die das automatische Inkrementieren von Primärschlüsselattributen ermöglichen.

Unter dem Gesichtspunkt der Leistung, vermute ich, gibt es in den meisten Fällen wenig Unterschiede. Aber wie bei jedem Leistungsproblem sollten Sie messen, wo Sie Bedenken haben.

    
RoadWarrior 08.12.2008 22:33
quelle
3

Wie ich es verstehe (und wirklich, in der Praxis macht es Sinn), identifiziert der Primärschlüssel einige eindeutige Daten ... zumindest in einer normalisierten Tabelle. Sie sollten einen zusammengesetzten Primärschlüssel (einen Primärschlüssel mit mehreren Spalten) verwenden, wenn Sie Daten in der Tabelle haben, die explizit durch den Schlüssel identifiziert werden müssen.

Beispiel: In einer Tabelle, die aktuelle und vergangene Termine speichert, an denen ein Kunde mehr als einmal in der Tabelle erscheinen kann, können Sie eine Tabelle wie folgt einrichten:

AppointmentDate, CustomerID, AppointmentReason

Wo das AppointmentDate und die CustomerID zusammengesetzte Primärschlüssel sind und die eindeutigen Informationen von ApporturnReason identifizieren.

Wir verwenden AppointmentDate und CustomerID als primären zusammengesetzten Schlüssel, da mehrere Kunden gleichzeitig einen Termin am selben Tag haben können. Wenn wir nur ein AppointmentDate als Primärschlüssel verwendet haben, könnten wir auf ein Problem mit der Eindeutigkeitseinschränkung für den Primärschlüssel stoßen.

Für Ihre Situation würde es hilfreich sein, mehr Informationen darüber zu haben, welche Art von Daten enthalten sein soll. Ich kann jedoch die Benutzer-ID und die Ziel-ID zusammen mit der Ziel-ID, die ein Fremdschlüssel für die Tabelle UserRelations ist, zu einem zusammengesetzten Primärschlüssel machen in Ihrer Benutzertabelle. Ich würde dies tun, denn wenn Sie einen Primärschlüssel namens RelationID haben, werden Sie eine sich wiederholende Benutzerspalte haben, die die Leistung beeinträchtigen kann und Ihre Tabellen nicht normalisiert.

    
Dalin Seivewright 08.12.2008 21:39
quelle
2

Sie sollten immer versuchen, einen "aussagekräftigen" oder "natürlichen" Primärschlüssel oder eindeutigen Index für jede Tabelle zu erstellen, um die Integrität der Daten zu erhalten. Wenn dies einen mehrspaltigen (oder "zusammengesetzten") Schlüssel bedeutet, dann gibt es tatsächlich Auswirkungen auf die Leistung - insbesondere, wenn Sie denselben mehrspaltigen Schlüssel als Fremdschlüssel in anderen abhängigen Tabellen oder in Indizes für Suchprädikate in Abfragen usw. verwenden .

Wenn diese Implikationen für die Performance signifikant werden (vielleicht sogar bevor sie dies tun), sollten Sie für all diese anderen Zwecke (FKs, Joins, Indizes, ...) einen nicht sinnvollen "Surrogat" -Schlüssel verwenden (normalerweise eine ganze Zahl). Suchprädikate abfragen, Anwendungscode-Entität Identifiers, etc.)

, aber bewahren Sie immer den aussagekräftigen Schlüssel oder eindeutigen Index auf, um die Datenintegrität der Tabellen zu erhalten

    
Charles Bretana 08.12.2008 21:38
quelle
2

Ich habe mit der Verwendung von zusammengesetzten Primärschlüsseln für Tabellen, die Beziehungen beschreiben, gute Ergebnisse in Bezug auf die Leistung erzielt. Es gibt zwei Auswirkungen der Deklaration eines Primärschlüssels:

Sie erhalten Einschränkungen, die erfordern, dass jede der beteiligten Spalten nicht null ist und die Eindeutigkeit der beteiligten Spalten zusammen erfordert.

Sie erhalten einen Index, der bei gegebenem Primärschlüssel einen schnellen Zugriff auf die einzelne Zeile ermöglicht. Die meisten DBMS machen diesen Index für Sie.

Wie nützlich dieser Index ist, hängt vom Abfrageoptimierer, der Reihenfolge der Spalten in Ihrer Primärschlüsseldeklaration und dem Verwendungsmuster Ihrer Daten ab. Manchmal kann es nützlich sein, den automatischen Index durch selbst erstellte Indizes in anderen Spalten als der ersten in einem zusammengesetzten Primärschlüssel zu ergänzen.

Die Einschränkungen, die Sie erhalten, wenn Sie einen zusammengesetzten Primärschlüssel deklarieren, sind im Allgemeinen nützlicher als die, die Sie erhalten, indem Sie einen Ersatzschlüssel erstellen und diesen als Primärschlüssel deklarieren.

Auch dies bezieht sich auf Tabellen, die Beziehungen zwischen oder unter Entitäten beschreiben. Tabellen, die Entitäten beschreiben, sollten einen einfachen Primärschlüssel haben. Vorzugsweise ein natürlicher Schlüssel, aber in Fällen, in denen die gegebenen Daten keinen zuverlässigen Schlüssel liefern, kann ein Ersatzschlüssel notwendig sein.

    
Walter Mitty 09.12.2008 13:18
quelle
1

Der Primärschlüssel ist eine Kombination aus Index und Eindeutigkeitsbedingung. Das Hinzufügen der RelationID-Spalte hilft Ihnen nicht dabei, die Eindeutigkeit beizubehalten (da Paare der gleichen UserID + TargetID noch eingefügt werden können - sie erhalten nur unterschiedliche RelationIDs) oder hilft beim Datenzugriff (da Index auf UserID benötigt wird, wenn Sie zwischen Benutzern VERBINDEN) und Benutzerbeziehungen). So eine zweite scheint die bessere Lösung zu sein.

    
Dmitry Khalatov 08.12.2008 21:33
quelle
1

Um nur den Topf zu rühren, brauchen Sie wahrscheinlich eine dritte Spalte hier: "Beziehung". Jedes Mal, wenn ich eine Benutzer-Beziehungstabelle habe, habe ich zwei Benutzer mit mehreren Beziehungen und muss sie getrennt halten:

%Vor%

Irgendwann endet die Patenschaft, aber Sie brauchen noch den Sponsor-Link. Während es jetzt nur einen Beziehungstyp gibt, wird sich das wahrscheinlich in Zukunft ändern. Ihr Primärschlüssel wird also UserId, TargetId, RelationshipType.

    
jmucchiello 08.12.2008 22:26
quelle
1

Ich werde hier meine zwei Cent durchgehen, weil ich glaube, dass es eine Gestalt in den kombinierten anderen Antworten gibt, die nicht klar dargestellt wird.

  1. Verwirrung entsteht, weil die Terminologie, die von Date, Codd und anderen entwickelt wurde, um das konzeptionelle Modell (dh Entitäten, Attribute, Beziehungen, Schlüssel) zu beschreiben, zwischenzeitlich von Herstellern zur Beschreibung der Eigenschaften der physischen Implementierung dieses Modells verwendet wurde ( Tabellen, Spalten, Datensätze, Indizes). Es ist wichtig zu verstehen, dass die beiden Bereiche separat und identifizierbar sind, wenn wir das Problem diskutieren.
  2. Die erste normale Form besagt, dass jede Relation im konzeptuellen Modell einen Primärschlüssel hat. Ein künstlicher Schlüssel , der nur im physischen Modell existiert, ist nicht qualifiziert; Beachten Sie jedoch, dass einige sogenannte künstliche Schlüssel NICHT im physikalischen Modell enthalten sind, sondern tatsächlich im konzeptionellen Modell. (Ein Beispiel hierfür ist SSN / SIN in den USA und Kanada, da die Einzigartigkeit im konzeptuellen Modell ohne sie nicht garantiert werden kann.) Um dies zu vermeiden, werde ich weiter unten auf einen Primärschlüssel aus dem konzeptuellen Modell verweisen der Natural Key . (Mehrere Kandidaten wären natürliche Kandidatenschlüssel.)
  3. Die Primärschlüsseleinschränkung in aktuellen RDBMS-Implementierungen dient mehreren Zwecken. Eine besteht darin, eine Eindeutigkeitsbeschränkung für physische Datensätze zu erzwingen, um eine Aktualisierung vor Ort aller Felder zu ermöglichen, die nicht Teil dieser (physischen) Primärschlüsseleinschränkung sind; Wenn es möglich ist, dass sich ein Feld eines Natural Key im Laufe der Zeit ändert, ist es zwingend erforderlich, dass kein solches Feld Teil der Primary Key Constraint im Physical Model ist.
  4. Eine weitere Verwendung der Primärschlüsseleinschränkung besteht darin, Fremdschlüssel-Lookups aus verwandten Tabellen zu aktivieren. Welches Ende wird am effizientesten durch die engste mögliche Primary Key Constraint erreicht? Zu diesem Zweck wählen Natural Keys die Primary Key Constraint schlecht aus, da sie normalerweise für eine optimale Indexgröße und -höhe zu breit sind (da es sich um Human Reaabale handelt).
  5. Daraus folge ich einer Folgerung: Die effizienteste Übersetzung des physikalischen Modells eines natürlichen Schlüssels aus dem konzeptuellen Modell ist normalerweise eine Eindeutigkeitsbedingung in Kombination mit einer eindeutigen und disjunkten künstlichen Primärschlüsseleinschränkung. Beachten Sie, dass in Fällen (z. B. SSN / SIN), in denen der Natural Key eine künstliche Komponente benötigt, eine zusätzliche künstliche Primärschlüsseleinschränkung erwünscht ist, die vollständig im Physical Model enthalten ist. dies, weil es notwendig ist, zu erlauben, dass die extern sichtbare künstliche Nummer geändert und / oder neu zugewiesen wird. (Wie viele wussten, dass US SSN einige Monate nach dem Tod wiederverwendet werden?)
Pieter Geerkens 22.03.2013 08:10
quelle
0

Wenn Sie unter Verwendung der Tabelle UserRelations eine Viele-zu-Viele-Beziehung zwischen Benutzern und Zielen erstellen, ist die erste falsch. Sie möchten, dass die UserID + TargetID eindeutig ist oder Sie mehrere redundante Einträge erhalten, die denselben Benutzer und dasselbe Ziel verbinden.

    
flussence 08.12.2008 21:25
quelle
0

Die geeignete Methode zum Verknüpfen von Benutzern - & gt; Ziele ist die zweite Option, die Sie haben, da dies die Methode ist, die die referenzielle Integrität der Nachschlagetabelle tatsächlich erzwingt.

Ohne einen Primärschlüssel oder eindeutig in den Spalten UserId und TargetId wären doppelte Einträge möglich, die höchstwahrscheinlich zu unerwarteten Ergebnissen führen würden.

    
Mitchel Sellers 08.12.2008 21:28
quelle
0

Speziell zu Ihrer Frage: Sie werden auf jeden Fall einen eindeutigen Schlüssel für die natürlichen Mehrfachspalten benötigen. Ob Sie es primär machen, liegt bei Ihnen.

Das Hinzufügen eines Ersatzschlüssels ist ein Stilproblem und wird oft von einigen Frameworks benötigt. Wenn Sie es hinzufügen, sollten Sie es in den meisten Fällen als primär festlegen, nur weil dies von den Frameworks erwartet wird. Funktional, solange beide einzigartig sind, macht es keinen Unterschied.

    
dkretz 08.12.2008 22:38
quelle

Tags und Links