Expressões do Tipo de Sequência (XQuery)
Aplica-se a:SQL Server
Em XQuery, um valor é sempre uma sequência. O tipo do valor é referido como um tipo de sequência. O tipo de sequência pode ser usado em uma instância de expressão XQuery. A sintaxe SequenceType descrita na especificação XQuery é usada quando você precisa se referir a um tipo em uma expressão XQuery.
O nome do tipo atómico também pode ser usado no como expressão XQuery. No SQL Server, a instância de e lançadas como expressões XQuery em SequenceTypes são parcialmente suportadas.
instância do Operador
A instância de operador pode ser usada para determinar o tipo dinâmico, ou de tempo de execução, do valor da expressão especificada. Por exemplo:
Expression instance of SequenceType[Occurrence indicator]
Observe que o operador instance of
, o Occurrence indicator
, especifica a cardinalidade, o número de itens na sequência resultante. Se isso não for especificado, a cardinalidade é assumida como 1. No SQL Server, apenas o ponto de interrogação (?) indicador de ocorrência é suportado. O ? indicador de ocorrência indica que Expression
pode retornar zero ou um item. Se o indicador de ocorrência ? for especificado, instance of
devolverá True quando o tipo de Expression
corresponder ao SequenceType
especificado, independentemente de Expression
devolver uma sequência única ou vazia.
Se o indicador de ocorrência ? não for especificado, sequence of
devolve True somente quando o tipo de Expression
corresponder ao Type
especificado e Expression
devolver um singleton.
Observação Os indicadores de ocorrência do símbolo de adição (+) e do asterisco (*) não são suportados no SQL Server.
Os exemplos a seguir ilustram o uso da instânciado operador XQuery.
Exemplo A
O exemplo a seguir cria uma variável xml type e especifica uma consulta em relação a ela. A expressão de consulta especifica um operador instance of
para determinar se o tipo dinâmico do valor retornado pelo primeiro operando corresponde ao tipo especificado no segundo operando.
A consulta a seguir retorna True, porque o valor 125 é uma instância do tipo especificado, xs:integer:
declare @x xml
set @x=''
select @x.query('125 instance of xs:integer')
go
A consulta a seguir retorna True, porque o valor retornado pela expressão, /a[1], no primeiro operando é um elemento:
declare @x xml
set @x='<a>1</a>'
select @x.query('/a[1] instance of element()')
go
Da mesma forma, instance of
retorna True na consulta a seguir, porque o tipo de valor da expressão na primeira expressão é um atributo:
declare @x xml
set @x='<a attr1="x">1</a>'
select @x.query('/a[1]/@attr1 instance of attribute()')
go
No exemplo a seguir, a expressão, data(/a[1]
, retorna um valor atômico que é digitado como xdt:untypedAtomic. Portanto, o instance of
retorna True.
declare @x xml
set @x='<a>1</a>'
select @x.query('data(/a[1]) instance of xdt:untypedAtomic')
go
Na consulta a seguir, a expressão, data(/a[1]/@attrA
, retorna um valor atômico não tipado. Portanto, o instance of
retorna True.
declare @x xml
set @x='<a attrA="X">1</a>'
select @x.query('data(/a[1]/@attrA) instance of xdt:untypedAtomic')
go
Exemplo B
Neste exemplo, você está consultando uma coluna XML digitada no banco de dados de exemplo AdventureWorks. A coleção de esquema XML associada à coluna que está sendo consultada fornece as informações de digitação.
Na expressão, data() retorna o valor digitado do atributo ProductModelID cujo tipo é xs:string de acordo com o esquema associado à coluna. Portanto, o instance of
retorna True.
SELECT CatalogDescription.query('
declare namespace PD="https://schemas.microsoft.com/sqlserver/2004/07/adventure-works/ProductModelDescription";
data(/PD:ProductDescription[1]/@ProductModelID) instance of xs:string
') as Result
FROM Production.ProductModel
WHERE ProductModelID = 19
Para obter mais informações, consulte Comparar XML digitado com XML não tipado.
As consultas a seguir usam a expressão Boolean instance of
para determinar se o atributo LocationID é do tipo xs:inteiro:
SELECT Instructions.query('
declare namespace AWMI="https://schemas.microsoft.com/sqlserver/2004/07/adventure-works/ProductModelManuInstructions";
/AWMI:root[1]/AWMI:Location[1]/@LocationID instance of attribute(LocationID,xs:integer)
') as Result
FROM Production.ProductModel
WHERE ProductModelID=7
A seguinte consulta é especificada na coluna XML tipada CatalogDescription. A coleção de esquema XML associada a esta coluna fornece informações de digitação.
A consulta usa o teste element(ElementName, ElementType?)
na expressão instance of
para verificar se o /PD:ProductDescription[1]
retorna um nó de elemento de tipo e nome específicos.
SELECT CatalogDescription.query('
declare namespace PD="https://schemas.microsoft.com/sqlserver/2004/07/adventure-works/ProductModelDescription";
/PD:ProductDescription[1] instance of element(PD:ProductDescription, PD:ProductDescription?)
') as Result
FROM Production.ProductModel
where ProductModelID=19
A consulta retorna True.
Exemplo C
Ao usar tipos de união, a expressão instance of
no SQL Server tem uma limitação: especificamente, quando o tipo de um elemento ou atributo é um tipo de união, instance of
pode não determinar o tipo exato. Consequentemente, uma consulta retornará False, a menos que os tipos atômicos usados no SequenceType sejam o pai mais alto do tipo real da expressão na hierarquia simpleType. Ou seja, os tipos atômicos especificados no SequenceType devem ser um filho direto de anySimpleType. Para obter informações sobre a hierarquia de tipos, consulte Type Casting Rules in XQuery.
O próximo exemplo de consulta executa o seguinte:
Crie uma coleção de esquema XML com um tipo de união, como um inteiro ou tipo de cadeia de caracteres, definido nela.
Declare uma variável de xml
digitada usando a coleção de esquema XML. Atribua uma instância XML de exemplo à variável.
Consulte a variável para ilustrar o comportamento
instance of
ao lidar com um tipo de união.
Esta é a consulta:
CREATE XML SCHEMA COLLECTION MyTestSchema AS '
<schema xmlns="http://www.w3.org/2001/XMLSchema" targetNamespace="http://ns" xmlns:ns="http://ns">
<simpleType name="MyUnionType">
<union memberTypes="integer string"/>
</simpleType>
<element name="TestElement" type="ns:MyUnionType"/>
</schema>'
Go
A consulta a seguir retorna Falso, porque o SequenceType especificado na expressão instance of
não é o ascendente máximo do tipo real da expressão fornecida. Ou seja, o valor do <TestElement
> é um tipo inteiro. O ancestral mais elevado é xs:decimal. No entanto, ele não é especificado como o segundo operando para o operador instance of
.
SET QUOTED_IDENTIFIER ON
DECLARE @var XML(MyTestSchema)
SET @var = '<TestElement xmlns="http://ns">123</TestElement>'
SELECT @var.query('declare namespace ns="http://ns"
data(/ns:TestElement[1]) instance of xs:integer')
go
Como o antecessor mais alto de xs:integer é xs:decimal, a consulta retornará True se a consulta for modificada para especificar xs:decimal como SequenceType na consulta.
SET QUOTED_IDENTIFIER ON
DECLARE @var XML(MyTestSchema)
SET @var = '<TestElement xmlns="http://ns">123</TestElement>'
SELECT @var.query('declare namespace ns="http://ns"
data(/ns:TestElement[1]) instance of xs:decimal')
go
Exemplo D
Neste exemplo, você primeiro cria uma coleção de esquema XML e usa-a para digitar uma variável xml instance of
.
A seguinte coleção de esquema XML define um tipo simples, myType, e um elemento, <root
>, do tipo myType:
drop xml schema collection SC
go
CREATE XML SCHEMA COLLECTION SC AS '
<schema xmlns="http://www.w3.org/2001/XMLSchema" targetNamespace="myNS" xmlns:ns="myNS"
xmlns:s="https://schemas.microsoft.com/sqlserver/2004/sqltypes">
<import namespace="https://schemas.microsoft.com/sqlserver/2004/sqltypes"/>
<simpleType name="myType">
<restriction base="s:varchar">
<maxLength value="20"/>
</restriction>
</simpleType>
<element name="root" type="ns:myType"/>
</schema>'
Go
Agora crie uma variável xml
DECLARE @var XML(SC)
SET @var = '<root xmlns="myNS">My data</root>'
SELECT @var.query('declare namespace sqltypes = "https://schemas.microsoft.com/sqlserver/2004/sqltypes";
declare namespace ns="myNS";
data(/ns:root[1]) instance of ns:myType')
go
Como o tipo myType deriva por restrição de um tipo varchar definido no esquema sqltypes, instance of
também retornará True.
DECLARE @var XML(SC)
SET @var = '<root xmlns="myNS">My data</root>'
SELECT @var.query('declare namespace sqltypes = "https://schemas.microsoft.com/sqlserver/2004/sqltypes";
declare namespace ns="myNS";
data(/ns:root[1]) instance of sqltypes:varchar?')
go
Exemplo E
No exemplo a seguir, a expressão recupera um dos valores do atributo IDREFS e usa instance of
para determinar se o valor é do tipo IDREF. O exemplo executa o seguinte:
Cria uma coleção de esquema XML em que o elemento <
Customer
> tem um atributo de tipo IDREFS OrderList, e o elemento <Order
> tem um atributo de tipo ID OrderID.Cria uma variável de xml
digitada e atribui uma instância XML de exemplo a ela. Especifica uma consulta em relação à variável. A expressão de consulta recupera o valor de ID da primeira ordem do atributo de tipo IDREFS OrderList do primeiro <
Customer
>. O valor recuperado é o tipo IDREF. Portanto,instance of
retorna True.
create xml schema collection SC as
'<schema xmlns="http://www.w3.org/2001/XMLSchema" xmlns:Customers="Customers" targetNamespace="Customers">
<element name="Customers" type="Customers:CustomersType"/>
<complexType name="CustomersType">
<sequence>
<element name="Customer" type="Customers:CustomerType" minOccurs="0" maxOccurs="unbounded" />
</sequence>
</complexType>
<complexType name="OrderType">
<sequence minOccurs="0" maxOccurs="unbounded">
<choice>
<element name="OrderValue" type="integer" minOccurs="0" maxOccurs="unbounded"/>
</choice>
</sequence>
<attribute name="OrderID" type="ID" />
</complexType>
<complexType name="CustomerType">
<sequence minOccurs="0" maxOccurs="unbounded">
<choice>
<element name="spouse" type="string" minOccurs="0" maxOccurs="unbounded"/>
<element name="Order" type="Customers:OrderType" minOccurs="0" maxOccurs="unbounded"/>
</choice>
</sequence>
<attribute name="CustomerID" type="string" />
<attribute name="OrderList" type="IDREFS" />
</complexType>
</schema>'
go
declare @x xml(SC)
set @x='<CustOrders:Customers xmlns:CustOrders="Customers">
<Customer CustomerID="C1" OrderList="OrderA OrderB" >
<spouse>Jenny</spouse>
<Order OrderID="OrderA"><OrderValue>11</OrderValue></Order>
<Order OrderID="OrderB"><OrderValue>22</OrderValue></Order>
</Customer>
<Customer CustomerID="C2" OrderList="OrderC OrderD" >
<spouse>John</spouse>
<Order OrderID="OrderC"><OrderValue>33</OrderValue></Order>
<Order OrderID="OrderD"><OrderValue>44</OrderValue></Order>
</Customer>
<Customer CustomerID="C3" OrderList="OrderE OrderF" >
<spouse>Jane</spouse>
<Order OrderID="OrderE"><OrderValue>55</OrderValue></Order>
<Order OrderID="OrderF"><OrderValue>55</OrderValue></Order>
</Customer>
<Customer CustomerID="C4" OrderList="OrderG" >
<spouse>Tim</spouse>
<Order OrderID="OrderG"><OrderValue>66</OrderValue></Order>
</Customer>
<Customer CustomerID="C5" >
</Customer>
<Customer CustomerID="C6" >
</Customer>
<Customer CustomerID="C7" >
</Customer>
</CustOrders:Customers>'
select @x.query(' declare namespace CustOrders="Customers";
data(CustOrders:Customers/Customer[1]/@OrderList)[1] instance of xs:IDREF ? ') as XML_result
Limitações de implementação
Estas são as limitações:
Os schema-element() e schema-attribute() tipos de sequência não são suportados para comparação com o operador
instance of
.Sequências completas, por exemplo,
(1,2) instance of xs:integer*
, não são suportadas.Quando estiver a usar um formulário do elemento () da sequência do tipo que especifica um nome de tipo, como
element(ElementName, TypeName)
, o tipo deve ser qualificado com um ponto de interrogação (?). Por exemplo,element(Title, xs:string?)
indica que o elemento pode ser null. O SQL Server não oferece suporte à deteção em tempo de execução da propriedade xsi:nil ao usarinstance of
.Se o valor em
Expression
vier de um elemento ou atributo digitado como uma união, o SQL Server só poderá identificar o tipo primitivo, não derivado, do qual o tipo do valor foi derivado. Por exemplo, se <e1
> for definido como tendo um tipo estático de (xs:integer | xs:string), o seguinte retornará False.data(<e1>123</e1>) instance of xs:integer
No entanto,
data(<e1>123</e1>) instance of xs:decimal
retornará True.Para os tipos de sequência processing-instruction() e document-node(), somente formulários sem argumentos são permitidos. Por exemplo,
processing-instruction()
é permitido, masprocessing-instruction('abc')
não é permitido.
conversão para Operador
O convertido como expressão pode ser usado para converter um valor em um tipo de dados específico. Por exemplo:
Expression cast as AtomicType?
No SQL Server, o ponto de interrogação (?) é necessário após o AtomicType
. Por exemplo, conforme mostrado na consulta a seguir, "2" cast as xs:integer?
converte o valor da cadeia de caracteres em um inteiro:
declare @x xml
set @x=''
select @x.query('"2" cast as xs:integer?')
Na consulta a seguir, data() retorna o valor digitado do atributo ProductModelID, um tipo de cadeia de caracteres. O operador cast as
converte o valor em xs:integer.
WITH XMLNAMESPACES ('https://schemas.microsoft.com/sqlserver/2004/07/adventure-works/ProductModelDescription' AS PD)
SELECT CatalogDescription.query('
data(/PD:ProductDescription[1]/@ProductModelID) cast as xs:integer?
') as Result
FROM Production.ProductModel
WHERE ProductModelID = 19
O uso explícito de data() não é necessário nesta consulta. A expressão cast as
executa atomização implícita na expressão de entrada.
Funções do construtor
Você pode usar as funções do construtor de tipo atómico. Por exemplo, em vez de usar o operador cast as
, "2" cast as xs:integer?
, você pode usar a função de construtor xs:integer(), como no exemplo a seguir:
declare @x xml
set @x=''
select @x.query('xs:integer("2")')
O exemplo a seguir retorna um valor xs:date igual a 2000-01-01Z.
declare @x xml
set @x=''
select @x.query('xs:date("2000-01-01Z")')
Você também pode usar construtores para os tipos atômicos definidos pelo usuário. Por exemplo, se a coleção de esquema XML associada ao tipo de dados XML define um tipo simples, um construtor myType() pode ser usado para retornar um valor desse tipo.
Limitações de implementação
As expressões XQuery typeswitch, castablee treat não são suportadas.
lançado como requer um ponto de interrogação (?) após o tipo atómico.
xs:QName não é suportado como um tipo para conversão. Em vez disso, use de QName expandido.
xs:date, xs:timee xs:datetime requerem um fuso horário, que é indicado por um Z.
A consulta a seguir falha, porque o fuso horário não é especificado.
DECLARE @var XML SET @var = '' SELECT @var.query(' <a>{xs:date("2002-05-25")}</a>') go
Ao adicionar o indicador de fuso horário Z ao valor, a consulta funciona.
DECLARE @var XML SET @var = '' SELECT @var.query(' <a>{xs:date("2002-05-25Z")}</a>') go
Este é o resultado:
<a>2002-05-25Z</a>