Apakah urutan logis kolom dalam tabel memiliki dampak pada urutan fisik mereka di lapisan penyimpanan? Iya nih.
Apakah itu penting atau tidak adalah masalah yang berbeda yang belum bisa saya jawab (belum).
Dalam cara yang mirip dengan yang dijelaskan dalam artikel yang sering dikaitkan dari Paul Randal tentang anatomi catatan , mari kita lihat tabel dua kolom sederhana dengan DBCC IND:
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
Output di atas menunjukkan bahwa kita perlu melihat halaman 89:
DBCC TRACEON (3604);
GO
DBCC PAGE ('RowStructure', 1, 89, 3);
GO
Dalam output dari DBCC PAGE kita melihat c1 diisi dengan karakter 'A' sebelum c2's 'B':
Memory Dump @0x000000000D25A060
0000000000000000: 10001c00 01000000 41414141 41414141 †........AAAAAAAA
0000000000000010: 41414242 42424242 42424242 030000††††AABBBBBBBBBB...
Dan hanya karena, mari kita buka RowStructure.mdf
dengan editor hex dan konfirmasikan string 'A' mendahului string 'B':
Sekarang ulangi tes tetapi balik urutan string, menempatkan karakter 'B' di c1 dan karakter 'A' di c2:
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
Kali ini output PAGE DBCC kami berbeda dan string 'B' muncul lebih dulu:
Memory Dump @0x000000000FC2A060
0000000000000000: 10001c00 01000000 42424242 42424242 †........BBBBBBBB
0000000000000010: 42424141 41414141 41414141 030000††††BBAAAAAAAAAA...
Sekali lagi, hanya untuk cekikikan, mari kita periksa hex dump dari file data:
Seperti yang dijelaskan Anatomi Catatan , kolom panjang tetap dan variabel catatan disimpan dalam blok yang berbeda. Jenis kolom tetap dan variabel interleaving yang logis tidak memiliki kaitan dengan catatan fisik. Namun, dalam setiap blok urutan kolom Anda tidak memetakan ke urutan byte dalam file data.
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
Lihat juga:
Urutan kolom tidak masalah ... secara umum, tetapi - ITU TERGANTUNG!
CREATE TABLE
pernyataan (kecuali bahwa kolom kunci CI yang lebih dulu di bagian). Padahal urutan kolom bisa berubah jikaALTER COLUMN
mengubah tipe data / panjang kolom. Satu-satunya kasus kecil di mana hal itu penting yang dapat saya pikirkan adalah bahwa kolom pada akhir bagian panjang variabel dengan string kosong atau NULL tidak mengambil ruang sama sekali dalam array kolom offset (ditunjukkan oleh Kalen Delaney dalam buku internal 2008)C
tidak cocok, dan masuk ke halaman diperpanjang sendiri. Jadiselect A, B
dari YourTable` hanya membutuhkan setengah dari halaman yang dibacaselect A, C from YourTable
."Whether it matters or not is a different issue that I can't answer (yet)."
: Urutan kolom dapat secara signifikan mempengaruhi kinerja. Selain itu, bahkan dapat memengaruhi kesalahan! Lihat ini - Demo 2 menunjukkannya lebih baik menurut sayaJika Anda tidak mendefinisikan indeks berkerumun, Anda akan mendapatkan tabel tumpukan. Untuk tabel tumpukan, Anda akan selalu memindai saat membaca data dan dengan demikian seluruh baris akan dibaca, menjadikan urutan kolom sebagai titik diperdebatkan.
Segera setelah Anda menentukan indeks berkerumun, data secara fisik disusun ulang agar sesuai dengan urutan fisik kolom seperti yang Anda tentukan - dan pada titik ini, urutan fisik menjadi penting. Urutan fisik adalah yang menentukan kelayakan operator yang mencari berdasarkan predikat yang Anda gunakan.
Meskipun saya tidak ingat pernah membacanya di mana saja, saya berasumsi SQL Server tidak menjamin urutan fisik kolom untuk tumpukan, sedangkan itu akan dijamin untuk indeks. Untuk menjawab pertanyaan Anda, tidak, urutan kolom dalam definisi seharusnya tidak masalah karena mereka tidak masalah ketika membaca data (perhatikan bahwa ini hanya untuk tumpukan - indeks adalah masalah yang berbeda).
Perbarui
Sebenarnya Anda mengajukan dua pertanyaan - "apakah urutan logis kolom dalam tabel memiliki dampak pada pemesanan fisik mereka di lapisan penyimpanan" adalah tidak. Urutan logis, sebagaimana didefinisikan oleh metadata, tidak harus berada dalam urutan yang sama dengan yang fisik. Apa yang saya kumpulkan Anda sedang mencari jawaban adalah apakah urutan logis dalam CREATE TABLE menghasilkan urutan fisik yang sama pada penciptaan - yang saya tidak tahu, untuk tumpukan - meskipun dengan peringatan di atas.
sumber
Berdasarkan apa yang saya lihat dan membaca urutan kolom di SQL Server tidak ada bedanya. Mesin penyimpanan menempatkan kolom pada baris terlepas dari bagaimana mereka ditentukan dalam pernyataan CREATE TABLE. Yang sedang berkata, saya yakin ada beberapa kasus tepi yang sangat terisolasi di mana itu penting tetapi saya pikir Anda akan mengalami kesulitan mendapatkan jawaban pasti tunggal untuk ini. Paul Randal " Inside The Storage Engine"Kategori posting blog adalah sumber terbaik untuk semua detail tentang cara kerja mesin penyimpanan yang saya sadari. Saya pikir Anda harus mempelajari semua cara penyimpanan dan matriks yang bertentangan dengan semua kasus penggunaan." untuk menemukan kasus tepi di mana pesanan akan menjadi masalah. Kecuali jika kasus tepi tertentu ditunjukkan yang berlaku untuk situasi saya, saya hanya memesan kolom secara logis pada CREATE TABLE saya.
sumber
Saya paham apa yang kamu maksud. Dari perspektif desain, tabel yang terlihat seperti ini:
jauh lebih baik daripada tabel yang terlihat seperti ini:
Tetapi mesin Database tidak terlalu peduli dengan urutan kolom logis Anda jika Anda mengeluarkan tsql seperti ini:
Mesin hanya tahu di mana daftar FirstName disimpan di disk.
sumber