Saat mengerjakan rilis Log Transaksi dbForge, di antara tugas-tugas lainnya, tim kami harus memikirkan cara menyimpan data XML yang diketik dengan benar.
Untuk memulainya, perlu disebutkan bahwa SQL Server tidak menyimpan XML dalam format yang dimasukkan. String XML diuraikan, dipisah menjadi tag, dan dengan demikian disimpan dalam format terkompresi. Elemen deskripsi yang dianggap tidak perlu oleh server akan dibuang.
Perlu diingat juga bahwa, jika tipe data kolom ditetapkan sebagai XML sederhana, server akan menyimpan data ini sebagai string Unicode.
Contoh 1.
CREATE TABLE XmlValuesTable ( [uid] [int] IDENTITY PRIMARY KEY, v XML NOT NULL ); GO INSERT INTO XmlValuesTable (v) VALUES ('<note><float>123.456</float><time>01:23:45.789</time></note>'); INSERT INTO XmlValuesTable (v) VALUES ('<note><float>4.0000000000</float><time>01:23:45Z</time></note>');
Server akan menyimpan insert datanya sebagai berikut:
F0 04 6E006F0074006500 <- Name "note" EF 000001 <- Namespace 01 F8 01 <- tag 01 F0 05 66006C006F0061007400 <- Name "float" EF 000002 <- Namespace 02 F8 02 <- tag 02 11 07 3100320033002E00340035003600 <- string "123.456" F7 <- closing tag F0 04 740069006D006500 <- Name "time" EF 000003 <- Namespace 02 F8 03 <- tag 03 11 0C 300031003A00320033003A00340035002E00370038003900 <- string "01:23:45.789" F7 <- closing tag F7 <- closing tag
Dalam contoh berikut, tipe data kolom ditentukan sebagai yang diketik melalui XML Schema Collection.
Contoh 2.
CREATE XML SCHEMA COLLECTION [XmlValuesSchemaCollection_datetime2] AS '<?xml version="1.0"?> <xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:sqltypes="http://schemas.microsoft.com/sqlserver/2004/sqltypes" <xsd:element name="datetime2" type="sqltypes:datetime2"/> </xsd:schema>'; GO CREATE TABLE XmlValuesTable_datetime2 ( [uid] [int] IDENTITY PRIMARY KEY, v XML(XmlValuesSchemaCollection_datetime2) NOT NULL ); GO INSERT INTO XmlValuesTable_datetime2 (v) VALUES (N'<datetime2>2014-06-18T06:39:05.190</datetime2>'); GO
Dalam kasus khusus ini, server akan menyimpan insert datanya sebagai berikut:
EA 09 014C010015 1A000000 <- type info 0x14C (332) “datetime2”, 0x15 (21) “dateTime” + offset F0 09 6400610074006500740069006D0065003200 <- Name "datetime2" EF 000001 <- Namespace 01 F8 01 <- tag 01 EA 05 004C010015 <- type info 7E 02978924A9380B <- "2014-06-18T06:39:05.190" F7 <- closing tag
Dengan cara ini, server mengonversi data yang disimpan ke tipe yang ditentukan dalam adendum artikel ini (Anda dapat melihat daftar semua tipe data dengan menjalankan kueri “pilih * dari sys.xml_schema_types” di server).
Mari kita lihat bagaimana server akan menyimpan struktur yang lebih kompleks mirip dengan yang ada di Contoh 1 dan dijelaskan dengan XML Schema Collection.
Contoh 3.
CREATE XML SCHEMA COLLECTION [XmlValuesSchemaCollection] AS '<?xml version="1.0"?> <xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:sqltypes="http://schemas.microsoft.com/sqlserver/2004/sqltypes" attributeFormDefault="unqualified" elementFormDefault="qualified"> <xsd:import namespace="http://schemas.microsoft.com/sqlserver/2004/sqltypes" schemaLocation="http://schemas.microsoft.com/sqlserver/2004/sqltypes/sql2008/sqltypes.xsd"/> <xsd:element name="note"> <xsd:complexType> <xsd:sequence> <xsd:element name="float" type="xsd:float"/> <xsd:element name="time" type="xsd:time"/> </xsd:sequence> </xsd:complexType> </xsd:element> </xsd:schema>'; GO CREATE TABLE XmlValuesTable ( [uid] [int] IDENTITY PRIMARY KEY, v XML(XmlValuesSchemaCollection) NOT NULL ); GO INSERT INTO XmlValuesTable (v) VALUES ('<note><float>123.456</float><time>01:23:45.789</time></note>');
Server akan menyimpan insert datanya sebagai berikut:
EA 05 0001000100 <- type info F0 04 6E006F0074006500 <- Name "note" EF 000001 <- Namespace F8 01 <- tag 01 EA 09 0111000011 12000000 <- type info 0x11 (17) "float" + offset F0 05 66006C006F0061007400 <- Name "float" EF 000002 <- Namespace F8 02 <- tag 02 EA 05 0011000011 <- type info 0x11 (17) "float" 03 79E9F642 <- "123.456" F7 <- closing tag EA 09 0116000016 10000000 <- type info 0x16 (22) "time" + offset F0 04 740069006D006500 <- Name "time" EF 000003 <- Namespace F8 03 <- tag 03 EA 05 0016000016 <- type info 0x16 (22) "time" 7D 03FDAF4C005B950A <- "01:23:45.789" F7 <- closing tag F7 <- closing tag
Mari kita coba menambahkan tautan skema ke sisipan.
Contoh 4.
INSERT INTO XmlValuesTable (v) VALUES ('<note xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"><float>123.456</float><time>01:23:45.789</time></note>');
EA 05 0001000100 <- type info F0 04 6E006F0074006500 <- Name "note" EF 000001 <- Namespace F8 01 <- tag 01 F0 09 78006D006C006E0073003A00780073006900 <- Name "xmlns:xsi" EF 000200 <- Namespace "xmlns:xsi" F6 02 <- Attribute 11 29 68007400740070003A002F002F007700770077002E00770033002E006F00720067002F0032003000300031002F0058004D004C0053006300680065006D0061002D0069006E007300740061006E0063006500 <- "http://www.w3.org/2001/XMLSchema-instance" F5 <- closing bracket EA 09 0111000011 12000000 <- type info 0x11 (17) "float" + offset F0 05 66006C006F0061007400 <- Name "float" EF 000003 <- Namespace F8 03 <- tag 03 EA 05 0011000011 <- type info 0x11 (17) "float" 03 79E9F642 <- "123.456" F7 <- closing tag EA 09 0116000016 10000000 <- type info 0x16 (22) "time" + offset F0 04 740069006D006500 <- Name "time" EF 000004 <- Namespace F8 04 <- tag 08 EA 05 0016000016 <- type info 0x16 (22) "time" 7D 03FDAF4C005B950A <- "01:23:45.789" F7 <- closing tag F7 <- closing tag
Seperti yang Anda lihat, server telah dengan hati-hati menyimpan namespace sebagai atribut dan menggunakan hampir setengah ruang untuk ini meskipun faktanya namespace tidak benar-benar melayani tujuan yang berguna di sini – data disimpan dengan cara yang sama. disimpan tanpa namespace.
Kesimpulan
Dari penjelasan di atas, tampaknya Anda dapat mengurangi ukuran database dengan menyimpan beberapa tipe data (misalnya float) sebagai nilai yang diketik karena 4 byte memerlukan penyimpanan yang jauh lebih sedikit daripada nilai yang sama yang disimpan sebagai string Unicode. Namun, Anda harus ingat bahwa tambahan 7-18 byte digunakan untuk setiap nilai untuk menjelaskan jenisnya dan memindahkannya ke posisi yang diperlukan.
tambahan
Korelasi tipe XML, tipe dasar, dan tipe data yang digunakan server untuk menyimpan nilai yang diketik.
Jenis XML | Tipe dasar | Disimpan sebagai jenis | Ukuran dalam byte | |
jenis apa saja | string | 2 * karakter | ||
anySimpleType | jenis apa saja | string | ||
string | anySimpleType | string | ||
boolean | anySimpleType | boolean | 1 | |
mengambang | anySimpleType | mengambang | 4 | |
dua kali lipat | anySimpleType | ganda | 8 | |
desimal | anySimpleType | SqlDesimal | 20 | |
durasi | anySimpleType | string | ||
tanggalWaktu | anySimpleType | *1 | ||
waktu | anySimpleType | *1 | ||
tanggal | anySimpleType | *1 | ||
gTahunBulan | anySimpleType | string | ||
gTahun | anySimpleType | string | ||
gBulanHari | anySimpleType | string | ||
gDay | anySimpleType | string | ||
gBulan | anySimpleType | string | ||
hexBinary | anySimpleType | array byte | ||
base64Binary | anySimpleType | array byte | ||
anyURI | anySimpleType | string | ||
QName | anySimpleType | string | ||
normalisasiString | string | string | ||
token | string | string | ||
bahasa | string | string | ||
Nama | string | string | ||
NCName | string | string | ||
ENTITAS | string | string | ||
NMTOKEN | string | string | ||
bilangan bulat | desimal | SqlDesimal | 20 | |
nonPositiveInteger | bilangan bulat | SqlDesimal | 20 | |
bilangan bulat negatif | nonPositiveInteger | SqlDesimal | 20 | |
panjang | bilangan bulat | SqlDesimal | 20 | |
int | panjang | SqlDesimal | 20 | |
pendek | int | SqlDesimal | 20 | |
byte | pendek | SqlDesimal | 20 | |
nonNegativeInteger | bilangan bulat | SqlDesimal | 20 | |
unsignedLong | nonNegativeInteger | SqlDesimal | 20 | |
unsignedInt | unsignedLong | SqlDesimal | 20 | |
unsignedShort | unsignedInt | SqlDesimal | 20 | |
unsignedByte | unsignedShort | SqlDesimal | 20 | |
Integer positif | nonNegativeInteger | SqlDesimal | 20 | |
chart | string | string | ||
nchar | string | string | ||
varchar | string | string | ||
nvarchar | string | string | ||
teks | string | string | ||
nteks | string | string | ||
varbiner | base64Binary | array byte | ||
biner | base64Binary | array byte | ||
gambar | base64Binary | array byte | ||
stempel waktu | base64Binary | array byte | ||
timestampNumeric | panjang | SqlDesimal | 20 | |
numerik | desimal | SqlDesimal | 20 | |
besar | panjang | SqlDesimal | 20 | |
kecil | pendek | SqlDesimal | 20 | |
kecil | unsignedByte | SqlDesimal | 20 | |
sedikit | boolean | boolean | 1 | |
nyata | mengambang | mengambang | 4 | |
waktu tanggal | tanggalWaktu | *1 | ||
waktu kecil | tanggalWaktu | *1 | ||
uang | desimal | SqlDesimal | ||
uang kecil | desimal | SqlDesimal | ||
pengidentifikasi unik | desimal | string | ||
datetime2 | tanggalWaktu | *1 | ||
datetimeoffset | tanggalWaktu | *1 | ||
hierarkiid | string | string | ||
dbobject | anyURI | string |
*1 – informasi data/waktu. Jenis spesifik ditentukan oleh nilainya.
Nilai | Disimpan sebagai jenis | Ukuran dalam byte |
TanggalOffset | Tanggal (jumlah hari) | 3 |
DateOffset (2019-09-16+02:00) | DateTimeOffset | 11 |
TanggalWaktu | TanggalWaktu | 7-9 tergantung dari presisi |
DateTimeOffset | DateTimeOffset | 9 |
Waktu | TanggalWaktu | 7-9 tergantung dari presisi |
Offset Waktu (01:23:45Z) | DateTimeOffset | 9 |