pengindeksan terhadap string peka huruf besar kecil namun kasus data tetap ada. Bagaimana cara kerjanya?
Ini sebenarnya bukan perilaku khusus SQL Server, hanya bagaimana hal-hal ini bekerja secara umum.
Jadi, data adalah data. Jika Anda berbicara tentang indeks khusus, data perlu disimpan karena yang lain itu akan membutuhkan tampilan-up di meja utama setiap kali untuk mendapatkan nilai yang sebenarnya, dan tidak akan ada kemungkinan indeks yang meliputi (di paling tidak untuk tipe string).
Data, baik dalam tabel / indeks berkerumun atau indeks non-berkerumun, tidak mengandung informasi collation / sorting. Ini hanyalah data. Kolasi (aturan lokal / budaya dan sensitivitas) hanyalah meta data yang dilampirkan pada kolom dan digunakan saat operasi sortir dipanggil (kecuali diganti olehCOLLATE
klausa), yang akan mencakup pembuatan / pembangunan kembali indeks. Aturan yang didefinisikan oleh non-binary collation digunakan untuk menghasilkan kunci sortir, yang merupakan representasi biner dari string (kunci sortir tidak diperlukan dalam collations biner). Representasi biner ini menggabungkan semua aturan lokal / budaya dan sensitivitas yang dipilih. Tombol sortir digunakan untuk menempatkan catatan dalam urutan yang tepat, tetapi tidak dengan sendirinya disimpan dalam indeks atau tabel. Mereka tidak disimpan (setidaknya saya belum melihat nilai-nilai ini di indeks dan diberitahu bahwa mereka tidak disimpan) karena:
- Mereka tidak benar-benar diperlukan untuk menyortir karena mereka hanya akan berada dalam urutan yang sama dengan baris dalam tabel atau indeks. Tapi, urutan fisik indeks itu hanya penyortiran, bukan perbandingan.
- Sementara menyimpannya mungkin membuat perbandingan lebih cepat, itu juga akan membuat indeks lebih besar karena ukuran minimum untuk satu karakter adalah 5 byte, dan itu hanya "overhead" (dari struktur kunci sortir). Sebagian besar karakter masing-masing 2 byte, ditambah 1 byte jika ada aksen, ditambah 1 byte jika huruf besar. Misalnya, "e" adalah kunci 7-byte, "E" dan "é" keduanya 8 byte, dan "É" adalah kunci 9-byte. Karenanya, tidak layak menyimpan ini pada akhirnya.
Ada dua jenis kumpulan: SQL Server dan Windows.
SQL Server
SQL Server collations (orang-orang dengan nama dimulai dengan SQL_
) adalah lebih tua, pra-SQL Server 2000 cara menyortir / membandingkan (meskipun SQL_Latin1_General_CP1_CI_AS
adalah masih default instalasi pada US English OS, cukup sedih). Dalam model yang lebih tua, sederhana, non-Unicode ini, setiap kombinasi lokal, halaman kode, dan berbagai kepekaan diberikan pemetaan statis masing-masing karakter dalam halaman kode itu. Setiap karakter diberi nilai (yaitu mengurutkan bobot) untuk menunjukkan bagaimana persamaannya dengan yang lain. Perbandingan dalam model ini tampaknya melakukan operasi dua lintasan:
- Pertama, menghapus semua aksen (sehingga " ü " menjadi " u "), memperluas karakter seperti " Æ " menjadi " A " dan " E ", lalu melakukan pengurutan awal sehingga kata-kata berada dalam urutan alami (bagaimana Anda ingin berharap menemukannya di kamus).
- Kemudian, karakter demi karakter menentukan kesetaraan berdasarkan nilai-nilai yang mendasari ini untuk setiap karakter. Bagian kedua inilah yang dijelaskan oleh mustaccio dalam jawabannya .
Satu-satunya sensitivitas yang dapat disesuaikan dalam susunan ini adalah: "huruf" dan "aksen" ("lebar", "tipe kana" dan "pemilih variasi" tidak tersedia). Juga, tak satu pun dari kumpulan ini mendukung Karakter Tambahan (yang masuk akal karena itu adalah Unicode-spesifik dan kumpulan ini hanya berlaku untuk data non-Unicode).
Pendekatan ini hanya berlaku untuk VARCHAR
data non-Unicode . Setiap kombinasi unik lokal, halaman kode, sensitivitas huruf, dan sensitivitas aksen memiliki "ID sort" yang spesifik, yang dapat Anda lihat dalam contoh berikut:
SELECT COLLATIONPROPERTY(N'SQL_Latin1_General_CP1_CI_AS', 'SortID'), -- 52
COLLATIONPROPERTY(N'SQL_Latin1_General_CP1_CS_AS', 'SortID'), -- 51
COLLATIONPROPERTY(N'Latin1_General_100_CI_AS', 'SortID'); -- 0
Satu-satunya perbedaan antara dua pemeriksaan pertama adalah sensitivitas huruf. Susunan ketiga adalah susunan Windows dan karenanya tidak memiliki tabel pemetaan statis.
Juga, susunan ini harus mengurutkan dan membandingkan lebih cepat daripada susunan Windows karena pencarian sederhana untuk karakter untuk mengurutkan berat. Namun, susunan ini juga jauh kurang fungsional dan harus dihindari jika memungkinkan.
Windows
Windows collations (yang namanya tidak dimulai dengan SQL_
) adalah yang lebih baru (dimulai pada SQL Server 2000) cara menyortir / membandingkan. Dalam model Unicode yang lebih baru, kompleks, setiap kombinasi lokal, halaman kode, dan berbagai sensitivitas tidak diberikan pemetaan statis. Untuk satu hal, tidak ada halaman kode dalam model ini. Model ini memberikan nilai sortir default untuk setiap karakter, dan kemudian setiap lokal / budaya dapat menetapkan ulang nilai sortir ke sejumlah karakter. Ini memungkinkan banyak budaya untuk menggunakan karakter yang sama dengan cara yang berbeda. Ini memang memiliki pengaruh memungkinkan beberapa bahasa untuk diurutkan secara alami menggunakan susunan yang sama jika mereka tidak menggunakan karakter yang sama (dan jika salah satu dari mereka tidak perlu menetapkan ulang nilai apa pun dan cukup menggunakan default).
Nilai sortir dalam model ini bukan nilai tunggal. Mereka adalah array nilai yang menetapkan bobot relatif ke huruf dasar, diakritik apa pun (yaitu aksen), casing, dll. Jika collation-case-sensitive, maka bagian "case" dari array itu digunakan, jika tidak maka diabaikan ( karenanya, tidak sensitif). Jika collation peka terhadap aksen, maka bagian "diakritik" dari array digunakan, jika tidak maka diabaikan (karenanya, tidak sensitif).
Perbandingan dalam model ini adalah operasi multi-pass:
- Pertama, string dinormalisasi sehingga berbagai cara untuk mewakili karakter yang sama akan menyamakan. Misalnya, " ü " dapat berupa satu karakter / titik kode (U + 00FC). Anda juga bisa menggabungkan non-beraksen " u " (U + 0075) dengan Diaresis Menggabungkan " ̈ " (U + 0308) untuk mendapatkan: " ü ", yang tidak hanya terlihat sama ketika diberikan (kecuali ada masalah dengan font Anda), tetapi juga dianggap sama dengan versi karakter tunggal (U + 00FC), kecuali jika menggunakan binary collation (yang membandingkan byte dan bukan karakter). Normalisasi memecah karakter tunggal menjadi berbagai bagian, yang mencakup ekspansi untuk karakter seperti " Æ " (seperti yang disebutkan di atas untuk kumpulan SQL Server).
- Operasi perbandingan dalam model ini berjalan karakter demi karakter per setiap sensitivitas . Sortir kunci untuk string ditentukan dengan menerapkan elemen yang sesuai dari setiap karakter susunan nilai array berdasarkan sensitivitas yang "sensitif". Nilai-nilai kunci sortir diatur oleh semua sensitivitas primer dari masing-masing karakter (karakter dasar), diikuti oleh semua sensitivitas sekunder (bobot diakritik), diikuti oleh berat case masing-masing karakter, dan seterusnya.
- Penyortiran dilakukan berdasarkan kunci penyortiran yang dihitung. Dengan masing-masing sensitivitas dikelompokkan bersama, Anda bisa mendapatkan urutan pengurutan yang berbeda dari yang Anda lakukan dengan susunan SQL Server yang setara saat membandingkan string beberapa karakter, dan aksen terlibat, dan susunan itu peka-aksen (dan bahkan lebih lagi jika susunannya adalah juga case-sensitive).
Untuk detail lebih lanjut tentang penyortiran ini, saya akhirnya akan menerbitkan posting yang menunjukkan nilai-nilai kunci semacam itu, bagaimana mereka dihitung, perbedaan antara SQL Server dan Windows collations, dll. Tetapi untuk sekarang, silakan lihat jawaban saya untuk: Accent Sensitive Sort ( harap dicatat bahwa jawaban lain untuk pertanyaan itu adalah penjelasan yang baik tentang algoritma Unicode resmi, tetapi SQL Server malah menggunakan algoritma kustom, meskipun serupa, dan bahkan tabel bobot kustom).
Semua sensitivitas dapat disesuaikan dalam susunan ini: "huruf", "aksen", "lebar", "tipe kana", dan "pemilih variasi" (mulai pada SQL Server 2017, dan hanya untuk koleksi Jepang). Juga, beberapa kumpulan ini (ketika digunakan dengan data Unicode) mendukung Karakter Tambahan (dimulai pada SQL Server 2012). Pendekatan ini berlaku untuk data NVARCHAR
dan VARCHAR
data (bahkan data non-Unicode). Ini berlaku untuk VARCHAR
data non-Unicode dengan terlebih dahulu mengkonversi nilai ke Unicode secara internal, dan kemudian menerapkan aturan sortir / perbandingan.
Tolong dicatat:
- Tidak ada susunan standar universal untuk SQL Server. Ada default instalasi yang berbeda berdasarkan pengaturan lokal / bahasa OS saat ini pada saat instalasi (yang sayangnya
SQL_Latin1_General_CP1_CI_AS
untuk sistem bahasa Inggris AS, jadi silakan pilih saran ini ). Ini dapat diubah selama instalasi. Susunan tingkat instance ini kemudian menetapkan susunan untuk [model]
DB yang merupakan templat yang digunakan saat membuat DB baru, tetapi susunan tersebut dapat diubah saat mengeksekusi CREATE DATABASE
dengan menentukan COLLATE
klausa. Kumpulan tingkat database ini digunakan untuk variabel dan string literal, serta default untuk kolom baru (dan diubah!) Ketika COLLATE
klausa tidak ditentukan (yang merupakan kasus untuk kode contoh dalam pertanyaan).
- Untuk info lebih lanjut tentang Collations / encode / Unicode, silakan kunjungi: Collations Info