Hat die logische Reihenfolge der Spalten in einer Tabelle Auswirkungen auf ihre physische Reihenfolge auf der Speicherebene? Ja.
Ob es darauf ankommt oder nicht, ist ein anderes Thema, das ich (noch) nicht beantworten kann.
Schauen wir uns eine einfache zweispaltige Tabelle mit DBCC IND an, ähnlich wie in dem häufig verlinkten Artikel von Paul Randal über die Anatomie eines Datensatzes beschrieben:
SET STATISTICS IO OFF;
SET STATISTICS TIME OFF;
USE master;
GO
IF DATABASEPROPERTY (N'RowStructure', 'Version') > 0 DROP DATABASE RowStructure;
GO
CREATE DATABASE RowStructure;
GO
USE RowStructure;
GO
CREATE TABLE FixedLengthOrder
(
c1 INT IDENTITY(1,1) PRIMARY KEY CLUSTERED
, c2 CHAR(10) DEFAULT REPLICATE('A', 10) NOT NULL
, c3 CHAR(10) DEFAULT REPLICATE('B', 10) NOT NULL
);
GO
INSERT FixedLengthOrder DEFAULT VALUES;
GO
DBCC IND ('RowStructure', 'FixedLengthOrder', 1);
GO
Die Ausgabe oben zeigt, dass wir uns Seite 89 ansehen müssen:
DBCC TRACEON (3604);
GO
DBCC PAGE ('RowStructure', 1, 89, 3);
GO
In der Ausgabe von DBCC PAGE sehen wir c1 gefüllt mit dem Zeichen 'A' vor c2 'B':
Memory Dump @0x000000000D25A060
0000000000000000: 10001c00 01000000 41414141 41414141 †........AAAAAAAA
0000000000000010: 41414242 42424242 42424242 030000††††AABBBBBBBBBB...
Und nur weil, lassen Sie RowStructure.mdf
uns mit einem Hex-Editor aufspringen und bestätigen, dass die 'A'-Zeichenfolge der' B'-Zeichenfolge vorausgeht:
Wiederholen Sie nun den Test, aber kehren Sie die Reihenfolge der Zeichenfolgen um, indem Sie die Zeichen 'B' in c1 und die Zeichen 'A' in c2 einfügen:
CREATE TABLE FixedLengthOrder
(
c1 INT IDENTITY(1,1) PRIMARY KEY CLUSTERED
, c2 CHAR(10) DEFAULT REPLICATE('B', 10) NOT NULL
, c3 CHAR(10) DEFAULT REPLICATE('A', 10) NOT NULL
);
GO
Diesmal ist unsere DBCC PAGE-Ausgabe anders und die 'B'-Zeichenfolge erscheint zuerst:
Memory Dump @0x000000000FC2A060
0000000000000000: 10001c00 01000000 42424242 42424242 †........BBBBBBBB
0000000000000010: 42424141 41414141 41414141 030000††††BBAAAAAAAAAA...
Lassen Sie uns noch einmal, nur um zu kichern, den Hex-Dump der Datendatei überprüfen:
Wie Anatomy of a Record erläutert, werden die Spalten mit fester und variabler Länge eines Datensatzes in unterschiedlichen Blöcken gespeichert. Das logische Verschachteln von festen und variablen Spaltentypen hat keine Auswirkung auf den physischen Datensatz. Innerhalb jedes Blocks entspricht die Reihenfolge Ihrer Spalten jedoch der Reihenfolge der Bytes in der Datendatei.
CREATE TABLE FixedAndVariableColumns
(
c1 INT IDENTITY(1,1) PRIMARY KEY CLUSTERED
, c2 CHAR(10) DEFAULT REPLICATE('A', 10) NOT NULL
, c3 VARCHAR(10) DEFAULT REPLICATE('B', 10) NOT NULL
, c4 CHAR(10) DEFAULT REPLICATE('C', 10) NOT NULL
, c5 VARCHAR(10) DEFAULT REPLICATE('D', 10) NOT NULL
, c6 CHAR(10) DEFAULT REPLICATE('E', 10) NOT NULL
);
GO
Memory Dump @0x000000000E07C060
0000000000000000: 30002600 01000000 41414141 41414141 †0.&.....AAAAAAAA
0000000000000010: 41414343 43434343 43434343 45454545 †AACCCCCCCCCCEEEE
0000000000000020: 45454545 45450600 00020039 00430042 †EEEEEE.....9.C.B
0000000000000030: 42424242 42424242 42444444 44444444 †BBBBBBBBBDDDDDDD
0000000000000040: 444444†††††††††††††††††††††††††††††††DDD
Siehe auch:
Spaltenreihenfolge spielt keine Rolle ... im Allgemeinen, aber - ES HÄNGT AB!
CREATE TABLE
Anweisung entspricht (mit der Ausnahme, dass CI-Schlüsselspalten im Abschnitt an erster Stelle stehen). Die Reihenfolge der Spalten kann sich jedoch ändern, wennALTER COLUMN
sich Datentypen / Spaltenlängen ändern . Der einzige kleine Fall , in dem es wichtig ist, dass ich mich vorstellen kann ist , dass Spalten am Ende des Abschnitts mit variabler Länge mit leeren String oder NULL überhaupt in der Spalte Offset - Array keinen Platz nehmen (nachgewiesen durch Kalen Delaney in den 2008 Interna buchen)C
passen also nicht und werden auf eine eigene erweiterte Seite verschoben . Alsoselect A, B
von YourTable` erfordert nur die halbe Seite liest ausselect A, C from YourTable
."Whether it matters or not is a different issue that I can't answer (yet)."
: Die Reihenfolge der Spalten kann die Leistung erheblich beeinträchtigen. Außerdem kann es sogar zu Fehlern kommen! Überprüfen Sie dies - Demo 2 zeigt es besser, denke ichWenn Sie keinen Clustered-Index definieren, erhalten Sie eine Heap-Tabelle. Bei einer Heap-Tabelle wird beim Lesen von Daten immer gescannt, und daher werden die gesamten Zeilen gelesen, sodass die Reihenfolge der Spalten ein Diskussionspunkt ist.
Sobald Sie einen Clustered-Index definieren, werden die Daten physisch so neu angeordnet, dass sie der physischen Reihenfolge der von Ihnen angegebenen Spalten entsprechen - und an dieser Stelle wird die physische Reihenfolge wichtig. Die physische Reihenfolge bestimmt die Berechtigung des suchenden Operators basierend auf den Prädikaten, die Sie verwenden.
Obwohl ich mich nicht erinnern kann, es irgendwo gelesen zu haben, würde ich annehmen, dass SQL Server die physische Reihenfolge der Spalten für Heaps nicht garantiert, wohingegen dies für Indizes garantiert wird. Nein, um Ihre Frage zu beantworten, sollte die Reihenfolge der Spalten in der Definition keine Rolle spielen, da sie beim Lesen der Daten keine Rolle spielen (beachten Sie, dass dies nur für Heaps gilt - Indizes sind eine andere Sache).
Update
Tatsächlich stellen Sie zwei Fragen: "Ob sich die logische Reihenfolge der Spalten in einer Tabelle auf ihre physische Reihenfolge auf der Speicherebene auswirkt" ist eine Nr. Die durch die Metadaten definierte logische Reihenfolge muss nicht mit der physischen Reihenfolge übereinstimmen. Sie suchen nach einer Antwort darauf, ob die logische Reihenfolge in CREATE TABLE bei der Erstellung dieselbe physische Reihenfolge ergibt, die ich nicht kenne, für Haufen - allerdings mit der obigen Einschränkung.
quelle
Basierend auf dem, was ich gesehen und gelesen habe, macht die Reihenfolge der Spalten in SQL Server keinen Unterschied. Das Speichermodul platziert Spalten in der Zeile, unabhängig davon, wie sie in der Anweisung CREATE TABLE angegeben sind. Abgesehen davon bin ich sicher, dass es einige sehr isolierte Randfälle gibt, in denen es wichtig ist, aber ich denke, Sie werden es schwer haben, eine einzige endgültige Antwort auf diese Fragen zu bekommen. Paul Randals " Inside The Storage Engine"Die Blogkategorie von Posts ist die beste Quelle für alle mir bekannten Details zur Funktionsweise der Speicher-Engine. Ich denke, Sie müssten die verschiedenen Funktionsweisen des Speichers untersuchen und diese gegen alle Anwendungsfälle aufteilen Um die Kantenfälle zu finden, bei denen die Reihenfolge eine Rolle spielt. Wenn nicht ein spezifischer Kantenfall angegeben wird, der für meine Situation gilt, ordne ich die Spalten einfach logisch auf meiner CREATE TABLE an. Ich hoffe, dies hilft.
quelle
Ich verstehe, was du meinst. Aus der Sicht des Designs eine Tabelle, die so aussieht:
ist viel besser als eine Tabelle, die so aussieht:
Das Datenbankmodul kümmert sich jedoch nicht wirklich um Ihre logische Spaltenreihenfolge, wenn Sie eine tsql wie diese ausgeben:
Die Engine weiß nur, wo die Liste der Vornamen auf der Festplatte gespeichert ist.
quelle