Surrogat vs natürlicher Schlüssel: harte Zahlen auf Leistungsunterschiede?

8

Es gibt eine gesunde Debatte zwischen Surrogat und natürlichen Schlüsseln:

SO Beitrag 1

SO Post 2

Meine Meinung, die im Einklang mit der Mehrheit zu stehen scheint (es ist eine knappe Mehrheit), ist, dass Sie Ersatzschlüssel verwenden sollten, es sei denn, ein natürlicher Schlüssel ist völlig offensichtlich und wird garantiert nicht geändert. Dann sollten Sie die Eindeutigkeit des natürlichen Schlüssels erzwingen. Das bedeutet fast immer Ersatzschlüssel.

Beispiel für die beiden Ansätze, beginnend mit einer Unternehmenstabelle:

1: Ersatzschlüssel: Tabelle hat ein ID-Feld, das die PK (und eine Identität) ist. Unternehmensnamen müssen nach Bundesstaat eindeutig sein, daher gibt es dort eine eindeutige Einschränkung.

2: Natürlicher Schlüssel: Tabelle verwendet CompanyName und State als PK - erfüllt sowohl die PK als auch die Eindeutigkeit.

Nehmen wir an, dass das Company PK in 10 anderen Tabellen verwendet wird. Meine Hypothese, die keine Zahlen enthält, ist, dass der Ersatzschlüsselansatz hier viel schneller wäre.

Das einzige überzeugende Argument, das ich für einen natürlichen Schlüssel gesehen habe, ist eine Tabelle für viele bis viele, die die zwei Fremdschlüssel als natürlichen Schlüssel verwendet. Ich denke in diesem Fall macht es Sinn. Aber Sie können in Schwierigkeiten geraten, wenn Sie umstrukturieren müssen; Das ist außerhalb des Umfangs dieses Posts, denke ich.

Hat jemand einen Artikel gesehen, der Leistungsunterschiede mit einer Reihe von Tabellen vergleicht, die Ersatzschlüssel verwenden vs. denselben Satz von Tabellen verwenden natürliche Schlüssel ? Sich auf SO umzuschauen und Google hat nichts lohnenswertes ergeben, nur eine Menge Theorie.

Wichtiges Update : Ich habe begonnen, eine Testtabelle zu erstellen, die diese Frage beantwortet. Es sieht so aus:

  • PartNatural - Teiltabelle, die verwendet die eindeutige PartNumber als PK
  • PartSurrogate - Teile Tabelle, die verwendet eine ID (int, identity) als PK und hat einen eindeutigen Index für die PartNumber
  • Werk - ID (int, identity) als PK
  • Engineer - ID (int, Identität) als PK

Jeder Teil ist mit einem Werk verbunden und jede Instanz eines Teils in einem Werk ist mit einem Ingenieur verbunden. Wenn jemand Probleme mit diesem Testbed hat, ist es jetzt an der Zeit.

    
jcollum 04.08.2009, 18:36
quelle

2 Antworten

9

Benutze beides! Natural Keys verhindern eine Beschädigung der Datenbank (Inkonsistenz könnte ein besseres Wort sein). Wenn der "richtige" natürliche Schlüssel (um doppelte Zeilen zu eliminieren) aufgrund der Länge oder der Anzahl der beteiligten Spalten aus Performance-Gründen schlecht ausgeführt wird, kann ein Ersatzschlüssel hinzugefügt werden, der als Fremdschlüssel in anderen Tabellen verwendet werden kann der natürliche Schlüssel ... Aber der natürliche Schlüssel sollte als alternativer Schlüssel oder eindeutiger Index verbleiben, um Datenkorruption zu verhindern und Datenbankkonsistenz zu gewährleisten ...

Ein Großteil des Hoohahs (in der "Debatte" zu diesem Thema) kann auf eine falsche Annahme zurückzuführen sein - dass Sie den Primärschlüssel verwenden müssen für Joins und Foreign Keys in anderen Tabellen. DAS IST FALSCH. Sie können ANY Schlüssel als Ziel für Fremdschlüssel in anderen Tabellen verwenden. Dies kann der Primärschlüssel, ein alternativer Schlüssel oder ein eindeutiger Index oder eine eindeutige Einschränkung sein. Und was Joins betrifft, können Sie alles für eine Join-Bedingung verwenden, es muss nicht einmal ein Schlüssel oder ein Idex oder sogar einzigartig sein !! (Wenn es jedoch nicht eindeutig ist, erhalten Sie mehrere Reihen in dem kartesischen Produkt, das es erstellt).

    
Charles Bretana 04.08.2009, 19:18
quelle
3

Natürliche Schlüssel unterscheiden sich von den Ersatzschlüsseln im Wert, nicht im Typ.

Jeder Typ kann für einen Ersatzschlüssel verwendet werden, z. B. ein VARCHAR für das systemgenerierte slug oder etwas anderes.

Die meisten verwendeten Typen für Ersatzschlüssel sind jedoch INTEGER und RAW(16) (oder welcher Typ auch immer RDBMS für GUID verwendet),

Der Vergleich von Ersatzintegern und natürlichen Ganzzahlen (wie SSN ) dauert genau die gleiche Zeit.

Beim Vergleich von VARCHAR s wird Kollation berücksichtigt und sie sind im Allgemeinen länger als ganze Zahlen, was sie weniger effizient macht.

Das Vergleichen eines Satzes von zwei INTEGER ist wahrscheinlich auch weniger effizient als der Vergleich eines einzelnen INTEGER .

Bei kleinen Datentypen ist dieser Unterschied wahrscheinlich Prozent der Prozente der Zeit, die benötigt wird, um Seiten abzurufen, Indizes zu durchqueren, Datenbank-Latches zu akzeptieren usw.

Und hier sind die Zahlen (in MySQL ):

%Vor%

t_source ist nur eine Dummy-Tabelle mit 1,000,000 rows.

aint und adouble , bint und bdouble enthalten genau dieselben Daten, außer dass aint eine ganze Zahl als PRIMARY KEY hat, während adouble ein Paar von zwei identischen ganzen Zahlen hat.

Auf meinem Rechner laufen beide Abfragen für 14,5 Sekunden, +/- 0,1 Sekunden

Der Leistungsunterschied liegt, falls vorhanden, innerhalb des Fluktuationsbereichs.

    
Quassnoi 04.08.2009 18:44
quelle