Ketik Aturan Casting di XQuery

Berlaku untuk:SQL Server

Diagram spesifikasi Fungsi dan Operator W3C XQuery 1.0 dan XPath 2.0 berikut menunjukkan jenis data bawaan. Ini termasuk jenis turunan primitif dan bawaan bawaan.

XQuery 1.0 type hierarchy

Topik ini menjelaskan aturan transmisi jenis yang diterapkan saat transmisi dari satu jenis ke jenis lainnya dengan menggunakan salah satu metode berikut:

  • Transmisi eksplisit yang Anda lakukan dengan menggunakan cast sebagai atau fungsi konstruktor jenis (misalnya, xs:integer("5")).

  • Transmisi implisit yang terjadi selama promosi jenis

Pengecoran Eksplisit

Tabel berikut menguraikan transmisi jenis yang diizinkan antara jenis primitif bawaan.

Describes casting rules for XQuery.

  • Jenis primitif bawaan dapat dilemparkan ke jenis primitif bawaan lainnya, berdasarkan aturan dalam tabel.

  • Jenis primitif dapat ditransmisikan ke jenis apa pun yang berasal dari jenis primitif tersebut. Misalnya, Anda dapat melemparkan dari xs:desimal ke xs:integer, atau dari xs:desimal ke xs:long.

  • Jenis turunan dapat dilemparkan ke jenis apa pun yang merupakan leluhurnya dalam hierarki jenis, hingga jenis dasar primitif bawaannya. Misalnya, Anda dapat melemparkan dari xs:token ke xs:normalizedString atau ke xs:string.

  • Jenis turunan dapat ditransmisikan ke jenis primitif jika leluhur primitifnya dapat ditransmisikan ke jenis target. Misalnya, Anda dapat mentransmisikan xs:integer, jenis turunan, ke xs:string, jenis primitif, karena xs:desimal, xs:integer primitif ancestor, dapat ditransmisikan ke xs:string.

  • Jenis turunan dapat ditransmisikan ke jenis turunan lain jika leluhur primitif jenis sumber dapat ditransmisikan ke nenek moyang primitif jenis target. Misalnya, Anda dapat melemparkan dari xs:integer ke xs:token, karena Anda dapat melemparkan dari xs:desimal ke xs:string.

  • Aturan untuk mentransmisikan jenis yang ditentukan pengguna ke jenis bawaan sama dengan untuk jenis bawaan. Misalnya, Anda dapat menentukan jenis myInteger yang berasal dari jenis xs:integer. Kemudian, myInteger dapat dilemparkan ke xs:token, karena xs:decimal dapat dilemparkan ke xs:string.

Jenis transmisi berikut tidak didukung:

  • Transmisi ke atau dari jenis daftar tidak diperbolehkan. Ini termasuk jenis daftar yang ditentukan pengguna dan jenis daftar bawaan seperti xs:IDREFS, xs:ENTITIES, dan xs:NMTOKENS.

  • Transmisi ke atau dari xs:QName tidak didukung.

  • xs:NOTATION dan subjenis durasi yang diurutkan sepenuhnya, xdt:yearMonthDuration dan xdt:dayTimeDuration, tidak didukung. Akibatnya, transmisi ke atau dari jenis ini tidak didukung.

Contoh berikut mengilustrasikan transmisi jenis eksplisit.

Contoh A

Contoh berikut mengkueri variabel jenis xml. Kueri mengembalikan urutan nilai jenis sederhana yang dititik sebagai xs:string.

declare @x xml  
set @x = '<e>1</e><e>2</e>'  
select @x.query('/e[1] cast as xs:string?')  
go  

Contoh B

Contoh berikut mengkueri variabel xml yang ditik. Contoh pertama-tama membuat koleksi skema XML. Kemudian menggunakan koleksi skema XML untuk membuat variabel xml yang diketik. Skema menyediakan informasi pengetikan untuk instans XML yang ditetapkan ke variabel. Kueri kemudian ditentukan terhadap variabel.

create xml schema collection myCollection as N'  
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema">  
      <xs:element name="root">  
            <xs:complexType>  
                  <xs:sequence>  
                        <xs:element name="A" type="xs:string"/>  
                        <xs:element name="B" type="xs:string"/>  
                        <xs:element name="C" type="xs:string"/>  
                  </xs:sequence>  
            </xs:complexType>  
      </xs:element>  
</xs:schema>'  
go  

Kueri berikut mengembalikan kesalahan statis, karena Anda tidak tahu berapa banyak elemen tingkat <root> atas dalam instans dokumen.

declare @x xml(myCollection)  
set @x = '<root><A>1</A><B>2</B><C>3</C></root>  
          <root><A>4</A><B>5</B><C>6</baz></C>'  
select @x.query('/root/A cast as xs:string?')  
go  

Dengan menentukan elemen singleton <root> dalam ekspresi, kueri berhasil. Kueri mengembalikan urutan nilai jenis sederhana yang dititik sebagai xs:string.

declare @x xml(myCollection)  
set @x = '<root><A>1</A><B>2</B><C>3</C></root>  
              <root><A>4</A><B>5</B><C>6</C></root>'  
select @x.query('/root[1]/A cast as xs:string?')  
go  

Dalam contoh berikut, variabel jenis xml menyertakan kata kunci dokumen yang menentukan kumpulan skema XML. Ini menunjukkan bahwa instans XML harus berupa dokumen yang memiliki satu elemen tingkat atas. Jika Anda membuat dua <root> elemen dalam instans XML, itu akan mengembalikan kesalahan.

declare @x xml(document myCollection)  
set @x = '<root><A>1</A><B>2</B><C>3</C></root>  
              <root><A>4</A><B>5</B><C>6</C></root>'  
go  

Anda dapat mengubah instans untuk menyertakan hanya satu elemen tingkat atas dan kueri berfungsi. Sekali lagi, kueri mengembalikan urutan nilai jenis sederhana yang dititik sebagai xs:string.

declare @x xml(document myCollection)  
set @x = '<root><A>1</A><B>2</B><C>3</C></root>'  
select @x.query('/root/A cast as xs:string?')  
go  

Transmisi Implisit

Transmisi implisit hanya diperbolehkan untuk jenis numerik dan jenis atom yang tidak diketik. Misalnya, fungsi min() berikut mengembalikan nilai minimum dari dua nilai:

min(xs:integer("1"), xs:double("1.1"))  

Dalam contoh ini, dua nilai yang diteruskan ke fungsi XQuery min() memiliki jenis yang berbeda. Oleh karena itu, konversi implisit dilakukan di mana jenis bilangan bulat dipromosikan menjadi dua kali lipat dan dua nilai ganda dibandingkan.

Jenis promosi seperti yang dijelaskan dalam contoh ini mengikuti aturan berikut:

  • Jenis numerik turunan bawaan dapat dipromosikan ke jenis dasarnya. Misalnya, bilangan bulat dapat dipromosikan ke desimal.

  • Desimal dapat dipromosikan ke float, dan float dapat dipromosikan menjadi dua kali lipat.

Karena transmisi implisit hanya diperbolehkan untuk jenis numerik, berikut ini tidak diizinkan:

  • Transmisi implisit untuk jenis string tidak diperbolehkan. Misalnya, jika dua jenis string diharapkan dan Anda meneruskan string dan token, tidak ada transmisi implisit yang terjadi dan kesalahan dikembalikan.

  • Transmisi implisit dari jenis numerik ke jenis string tidak diperbolehkan. Misalnya, jika Anda meneruskan nilai jenis bilangan bulat ke fungsi yang mengharapkan parameter jenis string, tidak ada transmisi implisit yang terjadi dan kesalahan dikembalikan.

Nilai casting

Saat transmisi dari satu jenis ke jenis lainnya, nilai aktual diubah dari ruang nilai jenis sumber ke ruang nilai jenis target. Misalnya, transmisi dari xs:desimal ke xs:double akan mengubah nilai desimal menjadi nilai ganda.

Berikut ini adalah beberapa aturan transformasi.

Mentransmisikan nilai dari string atau jenis untypedAtomic

Nilai yang ditransmisikan ke string atau jenis untypedAtomic diubah dengan cara yang sama seperti memvalidasi nilai berdasarkan aturan jenis target. Ini termasuk pola akhir dan aturan pemrosesan spasi putih. Misalnya, berikut ini akan berhasil dan menghasilkan nilai ganda, 1,1e0:

xs:double("1.1")

Saat transmisi ke jenis biner seperti xs:base64Binary atau xs:hexBinary dari string atau jenis untypedAtomic, nilai input harus dikodekan base64 atau hex.

Mentransmisikan nilai ke string atau jenis untypedAtomic

Transmisi ke string atau jenis untypedAtomic mengubah nilai ke representasi leksikal kanonis XQuery-nya. Secara khusus, ini dapat berarti bahwa nilai yang mungkin telah mematuhi pola tertentu atau batasan lain selama input tidak akan diwakili sesuai dengan batasan tersebut. Untuk memberi tahu pengguna tentang hal ini, SQL Server menandai jenis di mana batasan jenis dapat menjadi masalah dengan memberikan peringatan ketika jenis tersebut dimuat ke dalam kumpulan skema.

Saat mentransmisikan nilai jenis xs:float atau xs:double, atau salah satu subjenisnya, ke string atau jenis untypedAtomic, nilai diwakili dalam notasi ilmiah. Ini dilakukan hanya ketika nilai absolut nilai kurang dari 1,0E-6, atau lebih besar dari atau sama dengan 1,0E6. Ini berarti bahwa 0 diserialisasikan dalam notasi ilmiah ke 0,0E0.

Misalnya, xs:string(1.11e1) akan mengembalikan nilai "11.1"string , sementara xs:string(-0.00000000002e0) akan mengembalikan nilai string, "-2.0E-11".

Saat mentransmisikan jenis biner, seperti xs:base64Binary atau xs:hexBinary, ke string atau jenis untypedAtomic, nilai biner akan diwakili dalam bentuk base64 atau hex yang dikodekan, masing-masing.

Mentransmisikan nilai ke jenis numerik

Saat mentransmisikan nilai satu jenis numerik ke nilai jenis numerik lain, nilai dipetakan dari satu ruang nilai ke yang lain tanpa melalui serialisasi string. Jika nilai tidak memenuhi batasan jenis target, aturan berikut berlaku:

  • Jika nilai sumber sudah numerik dan jenis target adalah xs:float atau subtipe daripadanya yang memungkinkan nilai -INF atau INF, dan transmisi nilai numerik sumber akan mengakibatkan luapan, nilai dipetakan ke INF jika nilainya positif atau -INF jika nilainya negatif. Jika jenis target tidak mengizinkan INF atau -INF, dan luapan akan terjadi, pemeran gagal dan hasil dalam rilis SQL Server ini adalah urutan kosong.

  • Jika nilai sumber sudah numerik dan jenis target adalah jenis numerik yang mencakup 0, -0e0, atau 0e0 dalam rentang nilai yang diterima, dan transmisi nilai numerik sumber akan mengakibatkan aliran bawah, nilai dipetakan dengan cara berikut:

    • Nilai dipetakan ke 0 untuk jenis target desimal.

    • Nilai dipetakan ke -0e0 ketika nilainya adalah underflow negatif.

    • Nilai dipetakan ke 0e0 ketika nilainya adalah aliran bawah positif untuk jenis target float atau ganda.

    Jika jenis target tidak menyertakan nol dalam ruang nilainya, pemeran gagal dan hasilnya adalah urutan kosong.

    Perhatikan bahwa mentransmisikan nilai ke jenis titik float biner, seperti xs:float, xs:double, atau salah satu subjenisnya, mungkin kehilangan presisi.

Batasan Implementasi

Ini adalah batasannya:

  • Nilai titik mengambang NaN tidak didukung.

  • Nilai yang dapat dikebiri dibatasi oleh pembatasan implementasi jenis target. Misalnya, Anda tidak dapat melemparkan string tanggal dengan tahun negatif ke xs:date. Transmisi tersebut akan menghasilkan urutan kosong jika nilai disediakan pada waktu proses (alih-alih meningkatkan kesalahan run-time).

Lihat Juga

Menentukan Serialisasi Data XML