Gibt es ein SQL Server 2008-Äquivalent zur USING INDEX-Klausel in Oracle? Speziell für das Konstrukt:
CREATE TABLE c(c1 INT, c2 INT);
CREATE INDEX ci ON c (c1, c2);
ALTER TABLE c ADD CONSTRAINT cpk PRIMARY KEY (c1) USING INDEX ci;
In der SQL Server- Dokumentation zu eindeutigen Indizes heißt es (Hervorhebung hinzugefügt):
Eindeutige Indizes werden auf folgende Weise implementiert:
PRIMARY KEY oder UNIQUE Einschränkung
Wenn Sie eine PRIMARY KEY-Einschränkung erstellen, wird automatisch ein eindeutiger Clustered-Index für die Spalte oder Spalten erstellt, wenn noch kein Clustered-Index für die Tabelle vorhanden ist und Sie keinen eindeutigen Nonclustered-Index angeben . Die Primärschlüsselspalte kann keine NULL-Werte zulassen.
Dies scheint zu implizieren, dass es eine Möglichkeit gibt, anzugeben, welcher Index für einen Primärschlüssel verwendet werden soll.
create table c (c1 int not null primary key, c2 int)
Antworten:
Nein. Wenn Sie in SQL Server einen Primärschlüssel oder eine eindeutige Einschränkung erstellen, wird automatisch ein eindeutiger Index zur Unterstützung dieser Einschränkung mit denselben Schlüsseln erstellt.
Nein. In der Dokumentation wird nur versucht zu erklären, ob der automatische unterstützende Index als gruppiert oder nicht gruppiert erstellt wird, wenn Sie dies nicht angeben. Es ist verwirrend formuliert, ich stimme zu.
Wenn Sie einer vorhandenen Tabelle eine Primärschlüsseleinschränkung hinzufügen, ohne eine Präferenz auszudrücken, wird der unterstützende Index zur Verdeutlichung geclustert, wenn in der Tabelle kein bereits vorhandener gruppierter Index vorhanden ist. Der unterstützende Index wird als nicht gruppiert erstellt, wenn bereits ein gruppierter Index vorhanden ist
Sie können einen gruppierten oder nicht gruppierten Primärschlüssel speziell anfordern, indem Sie:
PRIMARY KEY CLUSTERED
oderPRIMARY KEY NONCLUSTERED
.Fairerweise ist die Dokumentation zu diesem Thema viel klarer:
table_constraint (Transact-SQL)
quelle
Die SQL Server-Syntax zum Erstellen eines Clustered-Index, der auch ein Primärschlüssel ist, lautet:
Was Ihren Kommentar betrifft: "Eine PK einen benannten Index verwenden lassen", führt der obige Code dazu, dass der Primärschlüsselindex "PK_c" heißt.
Der Primärschlüssel und der Clusterschlüssel müssen nicht dieselben Spalten sein. Sie können sie separat definieren. Ändern Sie im obigen Beispiel das
CLUSTERED
Schlüsselwort inNONCLUSTERED
und fügen Sie dann einfach einen Clustered-Index mit der folgendenCREATE INDEX
Syntax hinzu:In SQL Server der Clustered - Index ist der Tisch, sie sind ein-und-die-gleiche. Ein Clustered-Index definiert die logische Reihenfolge der in der Tabelle gespeicherten Zeilen. In meinem ersten Beispiel werden Zeilen in der Reihenfolge der Werte der Spalten
c1
und gespeichertc2
. Da der Clustering-Schlüssel auch als Primärschlüssel definiert ist, muss die Kombination vonc1
undc2
tabellenweit eindeutig sein.Im zweiten Beispiel besteht der Primärschlüssel aus den Spalten
c1
undc2
, der Clustering-Schlüssel ist jedoch nur diec2
Spalte. Da ich dasUNIQUE
Attribut in derCREATE INDEX
Anweisung nicht angegeben habe , muss der Clustering-Schlüssel (c2
) nicht in der gesamten Tabelle eindeutig sein. Ein "Eindeutiger" wird automatisch von SQL Server erstellt und an die Werte in derc2
Spalte angehängt , um den Clustering-Schlüssel zu erstellen. Dieser Clustering-Schlüssel wird, da er jetzt eindeutig ist, als Zeilen-ID in anderen in der Tabelle erstellten Indizes verwendet.Um zu beweisen, dass der Clustering-Schlüssel das Layout der im Speicher befindlichen Zeilen steuert, können Sie die undokumentierte Funktion verwenden
fn_PhysLocCracker(%%PHYSLOC%%)
. Der folgende Code zeigt, dass die Zeilen in der Reihenfolge derc2
Spalte, die ich als Clustering-Schlüssel definiert habe , auf der Festplatte angeordnet sind :Die Ergebnisse meiner Tempdb sind:
In der Abbildung oben werden die ersten drei Spalten von der
fn_PhysLocCracker
Funktion ausgegeben und zeigen die physische Reihenfolge der Zeilen auf der Festplatte. Sie können sehen, dass derslot_id
Wert den Sperrschritt mit dem Wert erhöhtc2
, der der Clustering-Schlüssel ist. Der Primärschlüsselindex speichert Zeilen in einer anderen Reihenfolge. Dies lässt sich feststellen, indem SQL Server gezwungen wird, Ergebnisse vom Scannen des Primärschlüssels zurückzugeben:Beachten Sie, dass ich
ORDER BY
in der obigen Anweisung keine Klausel verwendet habe, da ich versuche, die Reihenfolge der Elemente im Primärschlüsselindex anzuzeigen.Die Ausgabe der obigen Abfrage lautet:
Wenn
fn_PhysLocCracker
wir uns die Funktion ansehen, können wir die physikalische Reihenfolge des Primärschlüsselindex sehen.Da wir ausschließlich aus dem Index selbst lesen, dh in der Abfrage keine Spalten außerhalb des Index referenziert werden,
%%PHYSLOC%%
repräsentieren die Werte die Seiten im Index selbst.Die Ergebnisse:
quelle