Appendix B. Expression Reference

Introduction

This appendix describes all of the built-in XQuery keywords and operators, listed alphabetically (symbols first) for convenient reference. When a symbol occurs only in the context of others, for example, by occurs only in order by, then its entry may be omitted.

Each expression description begins with the syntax for the expression, followed by an explanation of its behavior, including optional parts and exceptional cases. In the syntax description, user-supplied parts of the expression appear in italics, and use the sequence type syntax described in Appendix A. In some expression syntaxes, additional descriptive words may be used as expression “types,” including stringliteral, sequencetype, and characters, with the obvious meanings.

Each expression is cross-referenced to related expressions and other parts of the book.

The inequality operator != first atomizes its operands, turning them into sequences of atomic values. It then tests whether there exists an atomic value in the first sequence, and independently whether there exists an atomic value in the second sequence, such that the two compare unequal with the operator ne.

Example B.1. inequality (!=) examples

'a' != 'b'                   => true
                           (: depends on the default collation :)

(1, 2, 3) != 4               => true
(1, 2, 3) != (1, 2, 4)       => true
(1, 2, 3) != ()              => false
xdt:untypedAtomic("2") != 2  => false
<a/> != <b/>                 => false

As shown in Listing B.1, the != operator has some surprising effects: not($a = $b) has a different effect from $a != $b; and != applied to elements can return false even when the elements have different names and attributes (see Chapter 11 for additional examples and explanation).

When comparing pairs of atomic values, if either one has the dynamic type xdt:untypedAtomic, then it is first promoted to some other type using a rule that is slightly different from that of the ne operator itself (which always promotes xdt:untypedAtomic to xs:string). Instead, != always promotes untyped values to xs:double if the other value is numeric, xs:string if the other value is also xdt:untypedAtomic, and otherwise to the same type as the other operand.

In this way, the simple expression $a != $b is equivalent to the more complex expression in Listing B.2, where promote-general() is a user-defined function for general comparisons that performs the promotion rules just described (see Appendix A).

Example B.2. An expression equivalent to $a != $b

some $i in fn:data($a), $j in fn:data($b)
satisfies promote-general($i, $j) ne promote-general($j, $i)

declare function promote-general($expr, $type) {
    typeswitch ($expr)
      case xdt:untypedAtomic return
        typeswitch($type)
          case xs:decimal        return cast as xs:double($expr)
          case xs:double         return cast as xs:double($expr)
          case xs:float          return cast as xs:double($expr)
          case xdt:untypedAtomic return cast as xs:string($expr)
          default                return same-type($expr, $type)
      default return $expr
};

See also: Chapter 5; ne and = (equality) in this appendix; fn:compare() and fn:deep-equal() in Appendix C; the section “Atomization” in Chapter 2; and Chapter 11.

The quote character is used around string literals and attribute content (in directly constructed attributes). Don't confuse the quotation mark (Unicode code point U+0022) with the so-called “smart-quote” characters used by some word processors (U+201C and U+201D).

In quoted strings, the quote character (") and ampersand (&) are special: the quote character because it denotes the end of the string, and the ampersand because it is used for entity references (named, hexadecimal, and decimal). If the string needs to contain the quote character, then either double it up ("") or use one of the three entity references: &quot;, &#x22;, or &#34;. Similarly, the ampersand can be escaped using one of the three entity references: &amp;, &#x26;, or &#38;.

All other characters (including new line characters, if the quoted string spans multiple lines) are part of the string value.

Example B.3. Quotation mark (") examples

"abcde"
"apostrophe (') needs no escape here, but quote ("") and ampersand (&amp;)
do"
<x y="z" />

See also: Chapter 1, and ' (apostrophe), "" (quote escape sequence), &quot; (quote entity reference), &#x (hexadecimal character reference), &# (decimal character reference), and &amp; (ampersand entity reference) in this appendix.

In a quoted string or attribute value, the quote character must be escaped or entitized to be used as a character in the string. The quote character can be escaped by doubling it ("").

Example B.4. Quote escape sequence ("") examples

"apostrophe (') needs no escape here, but quote ("") does"

See also: Chapter 1, and " (quotation mark) and &quot; (quote entity reference) in this appendix.

Variables in XQuery always begin with the dollar sign followed by a qualified name. If the name is prefixed, then the namespace of the variable is the in-scope namespace corresponding to that prefix (an error is raised if the prefix is not in scope). If the name is unprefixed, then the variable has no namespace part.

Variables can be introduced by the following expressions: FLWOR, quantification (some and every), typeswitch, and declare variable. Additionally, variables may be introduced into scope by import module (if the module contains global variable declarations) or through an implementation's API. Also, in the definition of a user-defined function, all the parameters passed to the function are assigned to variables that are in scope for the body of the function.

Once a variable is in scope, it cannot be redefined. Consequently, variable definitions are fixed and don't change (although in some cases, such as FLWOR and quantification, the variable may take on different values during the expression's evaluation).

Example B.5. Variable examples

$yourVariable
$my:variable

See also: Chapter 1; the section “Query Prolog” in Chapter 5; and declare function, declare variable, every, FLWOR, import module, some, and typeswitch in this appendix.

In strings and XML content, the decimal character reference can be used to represent any particular Unicode character. The character reference consists of the characters &# followed by one or more decimal digits (any of 0-9), and finally a semicolon (;). The integer value provided specifies the Unicode code point value represented by the reference.

The main reason to use character references is to conveniently represent characters that are difficult to type, or to distinguish them from other characters when the difference is not normally visible (for example, the nonbreaking space character &#160;).

The character represented by the character reference must still be a valid XML character; character references don't allow you to embed arbitrary binary data in XML (a common misconception). For that, you'll need to use a binary encoded type, such as xs:hexBinary or xs:base64Binary (see Appendix A).

Example B.6. Decimal character reference examples

"&#72;&#105;&#33;"

See also: Chapter 7; &#x (hexadecimal character reference), &amp;, &apos;, &gt;, &lt;, and &quot; in this appendix; and fn:codepoints-to-string() in Appendix C.

In strings and XML content, hexadecimal character references can be used to represent any particular character. The character reference consists of the characters &# followed by one or more hexadecimal characters (any of 0-9, a-f, or A-F), and finally a semicolon (;). The hexadecimal number provided specifies the Unicode code point value that is represented by the character reference.

The main reason to use character references is to conveniently represent characters that are difficult to type or to distinguish them from other characters when the difference is not normally visible (for example, the nonbreaking space character &#xA0;).

The character represented by the character reference must still be a valid XML character; character references don't allow you to embed arbitrary binary data in XML (a common misconception). For that, you'll need to use a binary encoded type, such as xs:hexBinary or xs:base64Binary (see Appendix A).

Example B.7. Hexadecimal character reference examples

"&#x6c;&#x33;&#x033;&#x74;&#x003F;"

See also: Chapter 7; &# (decimal character reference), &amp;, &apos;, &gt;, &lt;, and &quot; in this appendix; and fn:codepoints-to-string() in Appendix C.

The entity reference &amp; is used in string literals and XML constructors to denote the ampersand character (&).

Example B.8. &amp; examples

"&amp;"
<x>&amp;</x>

See also: Chapter 7, and &# (decimal character reference), &#x (hexadecimal character reference), &apos;, &gt;, &lt;, and &quot; in this appendix.

The entity reference &apos; is used in string literals and XML constructors to denote the apostrophe character (').

Example B.9. &apos; examples

"&apos;"
<x>&apos;</x>

See also: Chapter 7, and ' (apostrophe), '' (apostrophe escape), &# (decimal character reference), &#x (hexadecimal character reference), &amp;, &gt;, &lt;, and &quot; in this appendix.

The entity reference &gt; is used in string literals and XML constructors to denote the greater-than sign (>).

Example B.10. &gt; examples

"&gt;"
<x>&gt;</x>

See also: Chapter 7, and > (greater-than sign), &# (decimal character reference), &#x (hexadecimal character reference), &amp;, &apos;, &lt;, and &quot; in this appendix.

The entity reference &lt; is used in string literals and XML constructors to denote the less-than sign (<).

Example B.11. &lt; examples

"&lt;"
<x>&lt;</x>

See also: Chapter 7, and < (less-than sign), &# (decimal character reference), &#x (hexadecimal character reference), &amp;, &apos;, &gt;, and &quot; in this appendix.

The entity reference &quot; is used in string literals and XML constructors to denote the quotation mark (").

Example B.12. &quot; examples

"&quot;"
<x>&quot;</x>

See also: Chapter 7, and " (quotation mark), "" (quote escape), &# (decimal character reference), &#x (hexadecimal character reference), &amp;, &apos;, &gt;, and &lt; in this appendix.

The apostrophe character is used around string literals and attribute content (in directly constructed attributes). Do not confuse the apostrophe (Unicode code point U+0027) with the so-called “smart quote” characters used by some word processors (U+2018 and U+2019).

In apostrophed strings, the apostrophe character (') and ampersand (&) are special: the apostrophe character because it denotes the end of the string, and the ampersand because it is used for entity references (named, hexadecimal, and decimal). If the string needs to contain the apostrophe character, then either double it up ('') or use one of the three entity references: &apos;, &#x27;, or &#39;. Similarly, the ampersand can be escaped using one of the three entity references: &amp;, &#x26;, or &#38;.

All other characters (including new line characters, if the string spans multiple lines) are part of the string value.

Example B.13. Apostrophe (') examples

'abcde'
'quote (") needs no escape here, but apostrophe ('') and ampersand (&amp;) do'
<x y='z' />

See also: Chapter 1, and " (quotation mark), '' (apostrophe escape sequence), and &apos; (apostrophe entity reference) in this appendix.

Inside an apostrophe-delimited string or attribute value, the apostrophe character must be doubled-up to be used as a character in the string.

Example B.14. Apostrophe escape sequence ('') examples

'quote (") needs no escape here, but apostrophe ('') does'

See also: Chapter 1, and ' (apostrophe) and &apos; (apostrophe entity reference) in this appendix.

Parentheses are used in XQuery for several purposes. The empty parentheses () denote the empty sequence. Parentheses can be used as grouping operators to express the order in which expressions should be evaluated.

Parentheses are required by some expressions, such as if and typeswitch. Parentheses are also used in function definitions and invocations as a wrapper around the function arguments. And finally, parentheses are used in some node kind tests and sequence types, like node() and item(), which look like functions but are not.

Example B.15. Parentheses examples

()
(1 + 2) * (3 + 4)
if ($done) then () else repeat()
subsequence( (1,2,3), 2 )

See also: Chapter 1; declare function, if, typeswitch, and validate in this appendix; and the section “Operator Precedence” in Appendix E.

XQuery comments may appear anywhere that ignorable whitespace may appear, and also within element content (i.e., everywhere except inside literals, entity references, wildcards, and direct XML constructors other than elements). The entire comment is removed from the query during processing, and so contributes nothing to the query.

Comments are useful both for documentation purposes and for temporarily commenting out parts of your code during development. Comments may contain any character sequence except :) (which terminates the comment). Comments may also be nested to any depth.

XQuery comments should not be confused with XML comments, which are a kind of XML node.

Example B.16. XQuery comment examples

(: code is read by people; use comments wisely :)
((:this is an empty sequence (: containing nested comments :):))
<x a="(:not a comment:)">(:a comment:)<!--(:not a comment:)--></x>

See also: Chapter 1, and (:: (pragma/extension) and <!-- (XML comment constructor) in this appendix.

Pragmas are ignorable instructions to an XQuery implementation. If the implementation doesn't support the pragma, then it must ignore the pragma (except for parsing it). If the implementation does support the pragma, then the pragma will have whatever meaning the implementation has assigned to it. In contrast, if an implementation doesn't support an extension used by the query, then it must raise an error.

The distinction allows porting queries to other implementations; features the query requires should be extensions, while features that are optional should be pragmas. Pragmas are typically used for debugging and tracing, while extensions are typically used for function libraries and extended operators (such as DML and full-text search).

Example B.17. Examples of pragma and extension

(::pragma once::)
(:: pragma warn-level 4 ::)
(:: extension full-text ::)

See also: Chapter 5 and Chapter 14.

The asterisk character (*) has several uses in XQuery (see also wildcard and multiplication). One use is in type names. When a type name is followed by an asterisk, it represents a sequence of zero or more values of the given type.

Example B.18. * (asterisk) examples

declare function example($x as xs:integer*) { 2*3 };

See also: Chapter 2, Appendix A, and * (wildcard), * (multiplication), ? (question mark), and + (plus sign) in this appendix.

In paths (and element and attribute type tests), the wildcard (*) can be used as a name test. There are three variations of the wildcard: * matches any name, NCName:* matches names with any local part and the namespace corresponding to the given prefix, and *:NCName matches names with the given local part in any namespace.

When used in a path, the wildcard name test matches element nodes in all axes except the attribute axis, where it matches attribute nodes.

Example B.19. Wildcard examples

//*
x:*/*:y

See also: Chapter 3 and node() in Appendix A.

When used as a binary operator, the asterisk multiplies two expressions. Like all arithmetic operators, it first atomizes both operands. If either sequence of atomic values is empty, then it returns the empty sequence. If either sequence contains more than one value, then it raises an error.

Otherwise, if either operand is type xdt:untypedAtomic, it is converted to xs:double. If both operands are numeric, then they are promoted to a common type (see Appendix A). No other type conversions are performed; the two operands must support multiplication or an error is raised.

Example B.2. Multiplication examples

1 * 1                         => 1
1 * xdt:untypedAtomic("2")    => 2.0E0
1 * "2"                       => error
xs:dayTimeDuration("P3D") * 3 => xs:dayTimeDuration("P9D")

Multiplication is symmetrical. In the list below, the types may appear in either order. The pairs of types that support multiplication are:

  • Both numeric types (xs:decimal, xs:double, and xs:float, and subtypes of these)

  • xs:decimal and xdt:yearMonthDuration (resulting in xdt:yearMonthDuration)

  • xs:decimal and xdt:dayTimeDuration (resulting in xdt:dayTimeDuration)

See also: Chapter 5; + (addition), - (subtraction), div, idiv, mod, * (asterisk), and * (wildcard) in this appendix; and the section “Atomization” in Chapter 2.

The plus sign (+) has several uses in XQuery (see also unary plus and addition). One use is in type names. When a type name is followed by a plus sign, it represents a sequence of one or more values of the given type.

Example B.21. + (plus sign) examples

declare function example($x as xs:integer+) { 2+3 };

See also: Chapter 5; Appendix A; + (unary plus), + (addition), e notation, * (asterisk), and ? (question mark) in this appendix; and fn:one-or-more() in Appendix C.

When used as a unary operator, the plus sign has the following effects: First, it atomizes its operand, turning it into a sequence of atomic values. If the sequence is empty, then it results in the empty sequence. Otherwise, if the sequence has length greater than one, an error is raised.

If the value has dynamic type xdt:untypedAtomic, it is converted to xs:double. Otherwise, if the value is not numeric (i.e., not xs:decimal, xs:double, xs:float, or a subtype of these), then an error is raised.

Example B.22. Unary plus examples

+1                      => 1
+xdt:untypedAtomic("2") => 2.0E0
+"2"                    => error (: operand is not numeric :)
+current-time()         => error (: operand is not numeric :)

Unary plus can be a convenient way to force the static type of an expression to be numeric without writing treat as. Otherwise, it has no real purpose except symmetry with the unary minus operator (-).

See also: Chapter 5; - (unary minus), + (plus sign), and + (addition) in this appendix; and the section “Atomization” in Chapter 2.

When used as a binary operator, the plus sign adds two expressions. Like all arithmetic operators, it first atomizes both operands. If either sequence of atomic values is empty, then it returns the empty sequence. If either sequence contains more than one value, then it raises an error.

Otherwise, if either operand is type xdt:untypedAtomic, it is converted to xs:double. If both operands are numeric, then they are promoted to a common type (see Appendix A). No other type conversions are performed; the two operands must support addition or an error is raised.

Example B.23. Addition examples

1+1                      => 2
1+xdt:untypedAtomic("2") => 3.0E0
1+"2"                    => error (: operand is not numeric :)

xs:date("2004-05-13") + xs:dayTimeDuration("P17D")
=> xs:date("2004-05-30")

Addition is symmetrical. In the list below, the types may appear in either order. The pairs of types that support addition are:

  • Both numeric types (xs:decimal, xs:double, and xs:float, and subtypes of these)

  • xs:date and xdt:yearMonthDuration (resulting in xs:date)

  • xs:date and xdt:dayTimeDuration (resulting in xs:date)

  • xs:dateTime and xdt:yearMonthDuration (resulting in xs:dateTime)

  • xs:dateTime and xdt:dayTimeDuration (resulting in xs:dateTime)

  • xs:time and xdt:dayTimeDuration (resulting in xs:time)

  • xdt:yearMonthDuration and xdt:yearMonthDuration (resulting in xdt:yearMonthDuration)

  • xdt:dayTimeDuration and xdt:dayTimeDuration (resulting in xdt:dayTimeDuration)

Note that in XQuery, + does not perform string concatenation as it does in many other languages. For that purpose, use either the fn:concat() or fn:string-join() function.

See also: Chapter 5; - (subtraction), * (multiplication), div, idiv, mod, + (plus sign), and + (unary plus) in this appendix; and the section “Atomization” in Chapter 2.

XQuery uses the comma (,) symbol in two ways. One use is as a separator between items in a sequence. Because comma has the lowest precedence among all XQuery operators, you may need to enclose the sequence in parentheses.

Also, certain expressions, such as FLWOR, quantification (some, every), function invocation, and function definitions use commas to separate variable declarations and parameters. When used in this way, the items aren't actually in a sequence.

Example B.24. Comma examples

1, 2, 4                  (: used to separate items in a sequence :)
concat("a", "b")         (: used to separate parameters :)
subsequence((1, 2), 3)   (: used in both ways :)

See also: Chapter 1 and the section “Operator Precedence” in Appendix E.

When used as an unary operator, the minus sign has the following effects: First, it atomizes its operand, turning it into a sequence of atomic values. If the sequence is empty, then it results in the empty sequence. Otherwise, if the sequence has length greater than one, an error is raised.

If the value has dynamic type xdt:untypedAtomic, it is converted to xs:double. Otherwise, if the value isn't numeric (i.e., not xs:decimal, xs:double, xs:float, or a subtype of these), then an error is raised.

Finally, it negates the value.

Example B.25. Unary minus examples

-1                      => -1
-xdt:untypedAtomic("2") => -2.0E0
-"2"                    => error (: operand is not numeric :)
-current-time()         => error (: operand is not numeric :)

See also: Chapter 5; + (unary plus), - (hyphen), and - (subtraction) in this appendix; and the section “Atomization” in Chapter 2.

When used as a binary operator, the minus sign subtracts two expressions. Like all arithmetic operators, it first atomizes both operands. If either sequence of atomic values is empty, then it returns the empty sequence. If either sequence contains more than one value, then it raises an error.

Otherwise, if either operand is type xdt:untypedAtomic, it is converted to xs:double. If both operands are numeric, then they are promoted to a common type (see Appendix A). No other type conversions are performed; the two operands must support subtraction or an error is raised.

Example B.26. Subtraction examples

1-1                      => 0
1-xdt:untypedAtomic("2") => -1.0E0
1-"2"                    => error (: operand is not numeric :)

xs:date("2004-05-30") - xs:dayTimeDuration("P17D")
=> xs:date("2004-05-13")

Subtraction is asymmetrical. In the list below, the operand types must occur in order. The pairs of types that support subtraction are:

  • Both numeric types (xs:decimal, xs:double, xs:float, and subtypes of these)

  • xs:date and xs:date (resulting in xdt:dayTimeDuration)

  • xs:date and xdt:yearMonthDuration (resulting in xs:date)

  • xs:date and xdt:dayTimeDuration (resulting in xs:date)

  • xs:dateTime and xs:dateTime (resulting in xdt:dayTimeDuration)

  • xs:dateTime and xdt:yearMonthDuration (resulting in xs:dateTime)

  • xs:dateTime and xdt:dayTimeDuration (resulting in xs:dateTime)

  • xs:time and xs:time (resulting in xdt:dayTimeDuration)

  • xs:time and xdt:dayTimeDuration (resulting in xs:time)

To subtract two xs:dateTime values and get an xdt:yearMonthDuration, use the built-in function fn:subtract-dateTimes-yielding-yearMonthDuration().

See also: Chapter 5; + (addition), * (multiplication), div, idiv, mod, - (hyphen), and - (unary minus) in this appendix; the section “Atomization” in Chapter 2; and fn:subtract-dateTimes-yielding-dayTimeDuration() and fn:subtract-dateTimes-yielding-yearMonthDuration() in Appendix C.

In XPath 1.0, the dot operator (.) selected the current context node. In XQuery, its behavior is similar, except that the current context item can be an atomic value or the empty sequence (when the context sequence is empty).

The current context item is perhaps most useful in predicates, where it can be used to compare the value of the current node or pass it to a function. Be aware that the predicate [.] will filter by position when the current context item is numeric.

Example B.27. Current context item (.) examples

a[. = "x"]
a[contains(., "x")]
(1, "x", 4)[.]

See also: Chapter 3 and .. (navigation operator) in this appendix.

As in XPath 1.0, the .. operator is just an abbreviation for parent::node(). It navigates to the parent of the current context node. If the current context item isn't a node, then it raises an error.

Note that the path x/y/.. is not equivalent to the path x (a common misconception). Instead, the path is equivalent to the path x[y], because it selects x only when it has at least one y child element.

Example B.28. Parent navigation (..) examples

a[.. = "x"]
node()[.. and not(../..)]   (: matches only nodes at the top :)

See also: Chapter 3, and . (current context item) and parent (axis) in this appendix.

The slash operator (/) by itself or at the start of a path navigates to the root node of the fragment to which the current context node belongs, exactly like a call to the built-in fn:root() function. If the current context item is not a node, it raises an error. So, the path / is equivalent to fn:root(.), while the path /step is equivalent to fn:root(.)/step. Otherwise, the / operator has no real meaning except to separate steps in a path.

Example B.29. Slash (/) examples

/
/top
/comment()
a/b/c
a[@b = "x"]/c/@d

See also: Chapter 3 and fn:root() in Appendix C.

The double slash (//) operator is similar to the slash (/) operator in that it can begin a path or separate steps in a path. However, // is actually an abbreviation for /descendant-or-self::node()/, so, for example, a//b means a/descendant-or-self::node()/b. Unlike /, // must always have a step expression following it.

The path a//b is equivalent to a/descendant-or-self::node()/b, which is equivalent to a/descendant::b.

Example B.30. descendant-or-self (//) examples

//x      (: this selects every x element in document order :)
x//y     (: this selects every y element descendant of x :)

Although // is easy to write, it's also easy to misuse. In some implementations, //a is much slower than directly seeking to the a element (when you know the path in advance). On other implementations, the converse is true. (In still other implementations, both queries perform equally well when schema information is provided.) The path a//b is almost always slower than directly seeking to the b element (when you know the path in advance).

Also, // has some surprises, such as the difference between //x[1] and (//x)[1]. See Chapter 11 for additional examples and discussion.

Example B.31. //x[1] versus (//x)[1]

//x[1]   (: this selects the first x child element of each node :)
(//x)[1] (: this selects the first x element overall :)

See also: Chapter 3; / (slash), descendant, and descendant-or-self in this appendix; and Chapter 11.

The axis separator isn't really an operator. It exists to syntactically separate the axis name from the node test (which may also be a name). Whitespace is allowed between the separator and the axis and/or node test.

Example B.32. Axis separator (::) examples

child::w/descendant::x:y / attribute :: z

See also: Chapter 3, and attribute (axis), child, descendant, descendant-or-self, parent, and self in this appendix.

The less-than operator, <, first atomizes its operands, turning them into sequences of atomic values. It then tests whether there exists an atomic value in the first sequence, and independently whether there exists an atomic value in the second sequence, such that the first compares less than the second using the value comparison operator lt.

Because < is also used for other purposes (including element constructors), it is parsed differently depending on the character following it. For example, <a><<b/> is a parse error because << parses as the node comparison operator, while <a/>< <b/> (with a space between the two < characters) parses as expected.

Example B.33. Less-than (<) examples

'a' < 'b'                   => true
                            (: depends on the default collation :)
(1, 2, 3) < 4               => true
(1, 2, 3) < (1, 2, 4)       => true
(1, 2, 3) < ()              => false
xdt:untypedAtomic("2") < 2  => false
<a/> < <b/>                 => false

As shown in Listing B.1, the < operator has some surprising effects, especially with the empty sequence (see Chapter 11 for additional surprises and explanations).

When comparing pairs of atomic values, if either one has the dynamic type xdt:untypedAtomic, then it is first promoted to some other type using a rule that is slightly different from that of the lt operator itself (which always promotes xdt:untypedAtomic to xs:string). Instead, < always promotes untyped values to xs:double if the other value is numeric, to xs:string if the other value is also xdt:untypedAtomic, and otherwise to the same type as the other operand.

In this way, the simple expression $a < $b is equivalent to the more complex expression in Listing B.2, where promote-general() is a hypothetical user-defined function that performs the general comparison promotion rules just described.

Example B.34. An expression equivalent to $a < $b

some $i in fn:data($a), $j in fn:data($b)
satisfies promote-general($i, $j) lt promote-general($j, $i)

See also: Chapter 5; lt and <= (less than or equal to) in this appendix; fn:compare() and fn:deep-equal() in Appendix C; the section “Atomization” in Chapter 2; and Chapter 11.

XQuery uses almost the same syntax for constructing XML elements as XML does, with one exception: the curly brace characters, { and } , have special meaning for XQuery. They indicate that an XQuery compiler should parse the enclosed expression as an XQuery expression instead of as character content for the XML node. To use these characters as content, double them up.

In XQuery, the XML element syntax is called direct element constructor to distinguish it from the computed element constructor syntax that uses the element keyword. The computed syntax is capable of computing not only the element content, but also its name. The direct constructor syntax is equivalent to the computed syntax with a constant name.

Space characters in constructed XML elements may be stripped or preserved, depending on the xmlspace policy.

Example B.35. Direct XML element constructor examples

<x y="1">z</x>           => <x y="1">z</x>
<x y="1+1">1+1</x>       => <x y="1+1">1+1</x>
<x y="{1+1}">{1+1}</x>   => <x y="2">2</x>

See also: Chapter 7, and { (left curly brace), {{ (left curly brace escape sequence), }} (right curly brace escape sequence ), declare xmlspace, and element (constructor) in this appendix.

XQuery uses the same syntax for constructing XML comments as XML does. Unfortunately, XQuery doesn't provide any way to construct a comment node with computed content.

XML comments shouldn't be confused with XQuery comments. XML comments construct nodes; XQuery comments are ignored by the compiler.

Example B.36. Direct XML comment constructor examples

<!---->
<!-- this is an XML comment -->

See also: Chapter 7, and < (XML element constructor), <? (XML processing instruction constructor), <![CDATA[ (CDATA section constructor), and (: (XQuery comment) in this appendix.

XQuery uses the same syntax for constructing XML CDATA sections as XML does. Unfortunately, XQuery doesn't provide any way to construct a CDATA section with computed content.

XML CDATA sections exist only to allow you to avoid using lots of entity and character references. They cannot contain characters that are invalid for XML, and they cannot contain the sequence ]]> because that is used to signify the end of a CDATA section. One way to overcome the second limitation is to use two CDATA sections: <![CDATA[]]]]><![CDATA[>]]>.

Example B.37. Direct XML CDATA constructor example

<x><![CDATA[Special characters like &, <, and > do not require escaping in CDATA 
Direct XML CDATA constructor examplesections]]></x>

See also: Chapter 7 and text (constructor) in this appendix.

The node comparison operator << (“before”) takes two arguments, which must be either singleton nodes or the empty sequence. If either operand is empty, then << returns the empty sequence. Otherwise, it returns true if the first node appears before the second in document order, and false otherwise.

Example B.38. Before (<<) example

doc("foo.xml") << doc("foo.xml")  => false

See also: Chapter 5 and >> (after) in this appendix.

The less-than-equals operator, <=, first atomizes its operands, turning them into sequences of atomic values. It then tests whether there exists an atomic value in the first sequence, and independently whether there exists an atomic value in the second sequence, such that the first compares less than or equal to the second using the value comparison operator le.

Example B.39. Less-than-equals (<=) examples

'a' <= 'b'                   => true
                             (: depends on the default collation :)

(1, 2, 3) <= 4               => true
(1, 2, 3) <= (1, 2, 4)       => true
(1, 2, 3) <= ()              => false
xdt:untypedAtomic("2") <= 2  => true
<a/> <= <b/>                 => false

As shown in Listing B.1, the <= operator has some surprising effects, especially with the empty sequence (see Chapter 11 for additional surprises and explanations).

When comparing pairs of atomic values, if either one has the dynamic type xdt:untypedAtomic, then it is first promoted to some other type using a rule that is slightly different from that of the le operator itself (which always promotes xdt:untypedAtomic to xs:string). Instead, <= always promotes untyped values to xs:double if the other value is numeric, to xs:string if the other value is also xdt:untypedAtomic, and otherwise to the same type as the other operand.

In this way, the simple expression $a <= $b is equivalent to the more complex expression in Listing B.2, where promote-general() is a user-defined function for general comparisons that performs the promotion rules just described (see Appendix A).

Example B.40. An expression equivalent to $a <= $b

some $i in fn:data($a), $j in fn:data($b)
satisfies promote-general($i, $j) le promote-general($j, $i)

See also: Chapter 5; le and < (less-than) in this appendix; fn:compare() and fn:deep-equal() in Appendix C; the section “Atomization” in Chapter 2; and Chapter 11.

XQuery uses the same syntax for constructing XML processing instructions as XML does. Unfortunately, XQuery doesn't provide any way to construct a processing instruction node with computed content.

Example B.41. Direct XML processing instruction constructor examples

<? example ?>
<?process this?>

See also: Chapter 7, and < (XML element constructor) and <!-- (XML comment constructor) in this appendix.

The equality operator = first atomizes its operands, turning them into sequences of atomic values. It then tests whether there exists an atomic value in the first sequence, and independently whether there exists an atomic value in the second sequence, such that the first compares equal to the second using the value comparison operator eq.

Example B.42. Equals (=) examples

'a' = 'b'                   => false
                            (: depends on the default collation :)

(1, 2, 3) = 4               => false
(1, 2, 3) = (1, 2, 4)       => true
(1, 2, 3) = ()              => false
xdt:untypedAtomic("2") = 2  => true
<a/> = <b/>                 => false

As shown in Listing B.1, the = operator has some surprising effects, especially with the empty sequence (see Chapter 11 for additional surprises and explanations).

When comparing pairs of atomic values, if either one has the dynamic type xdt:untypedAtomic, then it is first promoted to some other type using a rule that is slightly different from that of the eq operator itself (which always promotes xdt:untypedAtomic to xs:string). Instead, = always promotes untyped values to xs:double if the other value is numeric, to xs:string if the other value is also xdt:untypedAtomic, and otherwise to the same type as the other operand.

In this way, the simple expression $a = $b is equivalent to the more complex expression in Listing B.2, where promote-general() is a user-defined function for general comparisons that performs the promotion rules just described (see Appendix A).

Example B.43. An expression equivalent to $a = $b

some $i in fn:data($a), $j in fn:data($b)
satisfies promote-general($i, $j) eq promote-general($j, $i)

See also: Chapter 5; eq and != (inequality) in this appendix; fn:compare() and fn:deep-equal() in Appendix C; the section “Atomization” in Chapter 2; and Chapter 11.

The greater-than operator, >, first atomizes its operands, turning them into sequences of atomic values. It then tests whether there exists an atomic value in the first sequence, and independently whether there exists an atomic value in the second sequence, such that the first compares greater than the second using the value comparison operator gt.

Example B.44. Greater-than (>) examples

'a' > 'b'                   => false
                             (: depends on the default collation :)

(1, 2, 3) > 4               => false
(1, 2, 3) > (1, 2, 4)       => true
(1, 2, 3) > ()              => false
xdt:untypedAtomic("2") > 2  => false
<a/> > <b/>                 => false

As shown in Listing B.1, the > operator has some surprising effects, especially with the empty sequence (see Chapter 11 for additional surprises and explanations).

When comparing pairs of atomic values, if either one has the dynamic type xdt:untypedAtomic, then it is first promoted to some other type using a rule that is slightly different from that of the gt operator itself (which always promotes xdt:untypedAtomic to xs:string). Instead, > always promotes untyped values to xs:double if the other value is numeric, to xs:string if the other value is also xdt:untypedAtomic, and otherwise to the same type as the other operand.

In this way, the simple expression $a > $b is equivalent to the more complex expression in Listing B.2, where promote-general() is a hypothetical user-defined function that performs the general comparison promotion rules just described.

Example B.45. An expression equivalent to $a > $b

some $i in fn:data($a), $j in fn:data($b)
satisfies promote-general($i, $j) gt promote-general($j, $i)

See also: Chapter 5; gt and >= (greater-than or equal to) in this appendix; fn:compare() and fn:deep-equal() in Appendix C; the section “Atomization” in Chapter 2; and Chapter 11.

The node comparison operator >> (“after”) takes two arguments, which must be either singleton nodes or the empty sequence. If either operand is empty, then >> returns the empty sequence. Otherwise, it returns true if the first node appears after the second in document order, and false otherwise.

Example B.46. After (>>) example

doc("foo.xml") >> doc("foo.xml")  => false

See also: Chapter 5, << (before) in this appendix, and Chapter 2.

The greater-than-equals operator, >=, first atomizes its operands, turning them into sequences of atomic values. It then tests whether there exists an atomic value in the first sequence, and independently whether there exists an atomic value in the second sequence, such that the first compares greater than or equal to the second using the value comparison operator ge.

Example B.47. Greater-than-equals (>=) examples

'a' >= 'b'                   => false
                             (: depends on the default collation :)

(1, 2, 3) >= 4               => false
(1, 2, 3) >= (1, 2, 4)       => true
(1, 2, 3) >= ()              => false
xdt:untypedAtomic("2") >= 2  => true
<a/> >= <b/>                 => false

As shown in Listing B.1, the >= operator has some surprising effects, especially with the empty sequence (see Chapter 11 for additional surprises and explanations).

When comparing pairs of atomic values, if either one has the dynamic type xdt:untypedAtomic, then it is first promoted to some other type using a rule that is slightly different from that of the ge operator itself (which always promotes xdt:untypedAtomic to xs:string). Instead, >= always promotes untyped values to xs:double if the other value is numeric, to xs:string if the other value is also xdt:untypedAtomic, and otherwise to the same type as the other operand.

In this way, the simple expression $a >= $b is equivalent to the more complex expression in Listing B.2, where promote-general() is a user-defined function for general comparisons that performs the promotion rules just described (see Appendix A).

Example B.48. An expression equivalent to $a >= $b

some $i in fn:data($a), $j in fn:data($b)
satisfies promote-general($i, $j) ge promote-general($j, $i)

See also: Chapter 5; ge and > (greater-than sign) in this appendix; fn:compare() and fn:deep-equal() in Appendix C; the section “Atomization” in Chapter 2; and Chapter 11.

When a type name is followed by a question mark, it represents a sequence of zero or one values of the given type.

Note that in a function, a parameter that occurs zero or one times must still occur; it isn't an optional parameter. For example, the function in Listing B.49 must still be passed two parameters, even if they are both empty.

The question mark also appears in XML processing instruction constructors, for example, <?pi?>.

Example B.49. ? (question mark) examples

declare function example($x as xs:integer?) external;
$y cast as xs:string?

See also: Chapter 2; * (asterisk), + (plus sign), and <? and ?> (XML processing instruction constructors) in this appendix; and fn:zero-or-one() in Appendix C.

The @ symbol is most commonly used as a convenient abbreviation for the attribute axis. It also appears in front of names in the attribute() type test, to emphasize that it matches attributes.

Example B.50. Attribute navigation examples

a[@b = 1]/@c

See also: Chapter 3, attribute (axis) in this appendix, and attribute() type test in Appendix A.

XQuery, like XPath, uses square brackets to enclose predicate expressions. The predicate is a postfix operator, applied after an expression (the sequence to be filtered) and containing an expression (the predicate expression).

The predicate expression is evaluated for each item in the sequence to be filtered, using that item as the current context item (and deriving the rest of the focus from it, including the context position). If the predicate evaluates to true, then the item is kept in the result; otherwise, it is omitted.

If the predicate evaluates to a numeric value, then it is true if the context position is equal to that number. Otherwise, the predicate is converted to boolean exactly like the fn:boolean() function.

Example B.51. Predicate examples

("a", "b", "c")[2]       => "b"
("a", "b", "c")[2.5]     => ()
("a", "b", "c")[false()] => ()
("a", "b", "c")[true()]  => ("a", "b", "c")

x[y]    (: selects x if it has a child element y :)
x[@y=1] (: selects x if it has an attribute y equal to 1 :)

When the entire predicate is the current context item and the sequence to be filtered contains atomic values, “surprising” results can occur, as shown in Listing B.52. Numbers are compared to the context position, and all other values are converted to boolean.

Example B.52. More predicate examples

(1, 5, 3, 4, 2)[.]      => (1, 3, 4)
("a", "", "b")[.]       => ("a", "b")
(true(), false(), 3)[.] => (true(), 3)

See also: Chapter 3, and . (current context item) in this appendix.

Curly braces are used in the following expressions: declare variable, declare function, and validate, and the computed node constructors (attribute, document, element, and text).

The most important use of curly braces is inside element and attribute content to denote that the enclosed expression should be evaluated as an XQuery expression, instead of just treated as ordinary characters. To use a curly brace as an ordinary character in element or attribute content, double it up (or use a character escape).

Example B.53. Curly brace examples

<x y="{1 div 2}">{ 1 + 1 }</x> => <x y="0.5">2</x>
<x y="{{">}}</x>               => <x y="{">}</x>

See also: Chapter 7; {{ (left curly brace escape sequence), }} (right curly brace escape sequence), < (XML element constructor) , attribute (constructor), declare function, declare variable, document (constructor), element (constructor), text (constructor), and validate in this appendix.

In direct element constructors, the curly brace characters are used to enclose XQuery expressions. Consequently, if the element needs to contain a curly brace character itself, it must be escaped. There's no named entity reference for the curly braces, and it's difficult to remember their decimal or hexadecimal character references, so XQuery allows these characters to be escaped by doubling them.

Example B.54. Left curly brace escape sequence examples

<x>{{</x>        => <x>{</x>
<x>{1}{{{2}</x>  => <x>1{2</x>

See also: Chapter 7, and }} (right curly brace escape sequence), { (left curly brace), and < (XML element constructor) in this appendix.

In direct element constructors, the curly brace characters are used to enclose XQuery expressions. Consequently, if the element needs to contain a curly brace character itself, it must be escaped. There's no named entity reference for the curly braces, and it's difficult to remember their decimal or hexadecimal character references, so XQuery allows these characters to be escaped by doubling them.

Example B.55. Right curly brace escape sequence examples

<x>}}</x>        => <x>}</x>
<x>{1}}}{2}</x>  => <x>1}2</x>

See also: Chapter 7, and {{ (left curly brace escape sequence), } (right curly brace), and < (XML element constructor) in this appendix.

The ancestor axis matches all ancestors of the current context node. The node test can be used to filter the ancestors further, for example, matching only those with a particular name or node kind.

XQuery implementations aren't required to support the ancestor axis; Chapter 10 provides a workaround.

Example B.56. ancestor axis examples

count(ancestor::*)
x[ancestor::y]/ancestor::z

See also: Chapter 3, Chapter 10, and ancestor-or-self and parent in this appendix.

The ancestor-or-self axis matches all ancestors of the current context node, as well as the node itself. XQuery implementations aren't required to support the ancestor-or-self axis; Chapter 10 provides a workaround.

Example B.57. ancestor-or-self axis examples

ancestor-or-self::foo/bar
count(ancestor-or-self::*)

See also: Chapter 3, Chapter 10, and ancestor and parent in this appendix.

The and operator first converts both of its operands to boolean using the fn:boolean() function (also known as the Effective Boolean Value). If either operand is true, then and returns true, otherwise it returns false.

Example B.58. and examples

true() and false()        => false
"" and 0.0                => false
"x" and 1.0               => true
() and (true(), true())   => false

The order in which the and operator evaluates its arguments is implementation-dependent, and implementations are also allowed (and encouraged) to “short-circuit” this operator (evaluating only one of its operands if that is enough to determine the overall result). Consequently, expressions like error() and false() and false() and error() may raise an error or may return false, depending on the implementation.

See also: Chapter 5, and fn:boolean()and fn:not() in Appendix C.

The attribute axis matches all attributes of the current context node. The node test can be used to filter the attributes further, for example, matching only those with a particular name.

It's common practice to use @ as an abbreviation instead of writing attribute. When using the abbreviation, no axis separator is required.

Example B.59. attribute axis examples

count(attribute::*)
x[attribute::y = 1 or attribute::z]
x[@y = 1 or @z]

See also: Chapter 3, and @ (at sign), child, descendant, descendant-or-self, parent, and self in this appendix.

The computed attribute constructor takes two arguments, the name and the content. The name expression can be an ordinary name, or an expression (enclosed in curly braces) that computes the name. Attributes with constant names can be constructed using the ordinary XML syntax, so the computed name case is the more interesting of the two.

When the name is computed, the name expression must result in either an xs:QName value or else an xs:string value which is then parsed into a QName using the in scope namespaces. If the name cannot be parsed or isn't a QName, then an error is raised. Otherwise, the resulting QName value is the name of the attribute.

The content expression is first atomized, and then each item in the (possibly empty) sequence of atomic values is converted to string and then concate nated together with spaces separating them. In other words, attribute name { $x } is equivalent to attribute name { string-join(" ", data($x)) }.

The type of the constructed attribute is xdt:untypedAtomic, regardless of the type of its content expression, and the attribute isn't validated (unless it is used in an expression such as element construction or validate).

Example B.60. Computed attribute constructor examples

<x>{ attribute foo { () } }</x>         => <x foo="" />
<x>{ attribute { "ab" } { "c", "d", 3 } => <x ab="c d 3" />

See also: Chapter 7; document (constructor), element (constructor), and text (constructor) in this appendix; and the section “Atomization” in Chapter 2.

The cast as operator takes two arguments: an expression and a single type (the target type).

It first atomizes the expression. If the result contains more than one atomic value, then an error is raised. If the atomized sequence is empty, then the cast succeeds (and results in the empty sequence) only if the single type is followed by the ? occurrence indicator. Otherwise, cast as attempts to convert this single value to the target type, and either succeeds (resulting in a value with that type) or else raises an error using one of the following three rules:

  1. If the expression type is equal to or derived from the target type, then cast as returns the value unchanged but with the target type.

  2. Otherwise, if the target type is a derived type and the expression type is (or is derived from) xs:string or xdt:untypedAtomic, or if the target type derives from the expression type (down-cast), then the conversion process first works lexically, converting the value to a space-normalized string and then validating that string according to the rules of the target type. Then, the lexical string is converted into a value of that type.

  3. Otherwise, the expression is first up-cast (if necessary) to its primitive supertype, using rule 1 above. Then it is converted to the primitive supertype of the target type according to the primitive conversion chart described in Appendix A. Then, it is down-cast (if necessary) to the target type, using rule 2 above.

These conversion steps can result in an error. For example, converting "2.0" into an xs:integer will fail because the decimal point isn't allowed in the lexical format for xs:integer. Converting "2004-02-30" into xs:date will fail because although the string satisfies the lexical constraints for xs:date, it isn't a valid xs:date value (the second month never has 30 days).

Example B.61. cast as examples

xs:string("2.0") cast as xs:decimal => 2.0
xs:string("2.0") cast as xs:integer => error
xs:string("2") cast as xs:decimal   => 2.0
xs:string("2") cast as xs:integer   => 2

See also: Chapter 9; castable as, treat as, and validate in this appendix; Chapter 11; and section A.4 in Appendix A.

The castable as operator takes two arguments, an expression and a single type. It returns true if the expression can be cast into that type (by the cast as operator), otherwise it returns false.

This operator is mainly used to avoid conversion errors by first testing whether an expression can be converted.

Example B.62. castable as examples

1.0 castable as xs:integer => true
1.5 castable as xs:integer => false

See also: Chapter 9, cast as in this appendix, and Chapter 2.

The child axis matches all children (element, text, comment, and processing-instruction nodes) of the current context node. The node test can be used to filter the children further, for example, matching only those with a particular name or node kind.

It's common practice to omit the child axis, because it is the default axis. When using the abbreviation, no axis separator is required.

Example B.63. child axis examples

count(child::*)
count(child::comment())
x[child::y]/child::z
x[y]/z

See also: Chapter 3, and / (slash), attribute, descendant, descendant-or-self, parent, and self in this appendix.

The computed comment constructor takes one argument, which becomes the content of the comment node. The content is first atomized. If the resulting sequence is empty, then the content is the empty string. Otherwise, each atomic value is cast to xs:string, concatenated together with a space character in between each consecutive pair, and the final result becomes the content of the constructed comment node.

Example B.64. Computed comment constructor examples

comment { "foo" }  => <!--foo-->
comment { (1, 2) } => <!--1 2-->

See also: Chapter 7, and attribute (constructor), document (constructor), element (constructor), namespace (constructor), pi (constructor), and text (constructor) in this appendix.

The base URI declaration sets the base-uri value of the static context, which is used by functions such as base-uri() and doc().

See also: Chapter 5, and base-uri() in Appendix C.

The query prolog may contain a default collation declaration, which specifies the default collation to be used in the query (for comparing strings). The value must be a string literal naming a collation supported by the implementation, or else an error is raised. At most one default collation declaration may be used.

When no default collation declaration is used, the default collation is implementation-defined. Many implementations will use the Unicode code point collation as their default; its URI is http://www.w3.org/2003/11/xpath-functions/collation/codepoint. The Unicode code point collation is the only collation implementations are required to support.

Example B.65. Default collation declaration example

declare default collation "http://www.unicode.org/lang/en-us";

See also: Chapter 8, and fn:default-collation()in Appendix C.

The query prolog may contain a default element namespace declaration, which specifies the default namespace to be used for all element names (including constructors and paths) and type names (in cast as and other expressions).

At most one default element namespace declaration may appear in the prolog. Element constructors may override the default namespace using xmlns.

Example B.66. Default element namespace declaration examples

declare default element namespace "http://www.w3c.org";
<x>
  <y xmlns="http://www.w3c.org" />
</x>

Unlike ordinary namespace declarations, the namespace string may be the empty string (which is also the default value), in which case the default element namespace is no namespace at all. Otherwise, the namespace must be a valid namespace URI.

See also: Chapter 5, and declare default function namespace and declare namespace in this appendix.

The query prolog may contain a default function namespace declaration, which specifies the default namespace to be used for all function names (function invocations and definitions) in the module. At most one default function namespace declaration may be used in the prolog.

Example B.67. Default function namespace declaration example

declare default function namespace "http://www.w3c.org";
foo("xyz")

Unlike ordinary namespace declarations, the namespace string may be the empty string, in which case the default function namespace is no namespace at all. Otherwise, the namespace must be a valid namespace URI.

If a default function namespace declaration isn't provided, then in the main module the default namespace is the same one that is bound to the built-in fn prefix (http://www.w3.org/2003/11/xpath-functions). In library modules, the default is the target namespace of the module.

The default function namespace must not cause two functions to have the same (unprefixed) name and number of arguments, or else an error is raised (duplicate function declaration).

See also: Chapter 5, and declare default element namespace, declare namespace, and module in this appendix.

Function definitions are specified after the query prolog but before the query body, using the declare function keyword.

Functions are defined by name. If the name doesn't have a prefix, then it isn't in a namespace; otherwise, it is in the namespace corresponding to that prefix. User-defined functions may not be overloaded (i.e., only one definition per name), may not override built-in functions, and always take a fixed number of arguments. In contrast, many built-in functions are overloaded (e.g., compare()) and one (concat()) takes a variable number of arguments.

User-defined functions declare zero or more parameters, which are then in scope for the entire function body. Untyped parameters have the most generic type (item*). All parameters must have different names.

User-defined functions have a return type. If omitted, then the return type of the function is the most generic type (item*). The function body must match (according to sequence type matching) its declared type or an error is raised.

Example B.68. User-defined functions are powerful

(: Compute $b raised to the $exp power :)
declare function pow($b as xs:integer,
                     $exp as xs:integer) as xs:integer {
  if ($exp > 1)
    then $b * pow($b, $exp – 1)
  else if ($expr = 1)
    then $b
  else
    1
};

To allow interoperability with other languages, XQuery allows you to declare externally defined functions by using the external keyword instead of a function body. It's up to implementations whether and how to handle externally defined functions (including translating XQuery types into other languages' types and vice versa).

See also: Chapter 4, and declare variable in this appendix.

Table B.1. Predefined namespaces

Prefix

Namespace

fn

http://www.w3.org/2003/11/xpath-functions

xdt

http://www.w3.org/2003/11/xpath-datatypes

xml

http://www.w3.org/XML/1998/namespace

xs

http://www.w3.org/2001/XMLSchema

xsi

http://www.w3.org/2001/XMLSchema-instance

The namespace declaration introduces a namespace prefix into scope, binding it to the given namespace URI. The string literal must be a valid, non-empty URI. Every namespace declaration in the prolog must use a different prefix, although elements may override prefix bindings using xmlns or the namespace constructor.

The namespace URI must not be the empty string. To define the default namespace, use declare default element namespace or declare default function namespace, depending on the desired effect.

Example B.69. Namespace declaration example

declare namespace p = "http://www.w3c.org";
<p:x>
  <p:y xmlns:p="http://www.aw.com" />
</p:x>

XQuery predefines the five namespaces listed in Table B.1. The first two of these are tied to the current version of the XQuery drafts in progress; the other three are final. All of these except for the xml prefix may be redefined using declare namespace.

See also: Chapter 5, declare default element namespace and declare default function namespace in this appendix, and fn:get-inscope-namespace-prefixes() in Appendix C.

The validation declaration specifies the default validation mode to be used with the validate operator and element constructors. The mode must be one of lax, skip, or strict. If no validation declaration is used, then the default validation mode is lax.

Example B.70. Validation examples

declare validation lax;
declare validation skip;
declare validation strict;

See also: Chapter 9, and validate and < (XML element constructor) in this appendix.

Global variable declarations introduce a variable name into global scope. Optionally, the variable declaration may be typed. Then the variable is either assigned a value, or else declared to be an external parameter whose value is provided at runtime. These are called global variables and global (external) parameters, respectively. The name “variable” is somewhat misleading, because the value doesn't vary.

If the type is omitted for a global variable, then its static type is the static type of its value. This type must be compatible with the type of the expression used for the variable value. If the type is omitted for a global parameter, then its static type is xs:anyType.

How external parameter values are supplied to the query depends entirely on the implementation, but an error is raised if a value isn't supplied or its type is incompatible with the static type.

Example B.71. Variable declaration examples

declare variable $meaningOfLife as xs:integer { 42 };
declare variable $my:zero { 0 };
declare variable $unknown external;
declare variable $userID as xs:string external;

See also: Chapter 5, and declare function and $ (variable) in this appendix.

The xmlspace declaration specifies how boundary whitespace characters in XML element and attribute constructors are handled. The mode must be either preserve or strip (strip is the default), meaning preserve or remove boundary whitespace, respectively.

Example B.72. xmlspace declaration examples

declare xmlspace strip;
declare xmlspace preserve;

See also: Chapter 7 and < (element constructor) in this appendix.

The descendant axis matches all descendants (element, text, comment, and processing-instruction nodes) of the current context node. The node test can be used to filter the descendants further (for example, matching only those with a particular name or node kind).

Note that the descendant axis excludes the current node itself; to include the current node, use the descendant-or-self axis. The descendant axis itself doesn't have an abbreviation, although often the // abbreviation ends up having that meaning; for example, a//b is equivalent to a/descendant::b (but only because its actual expansion, a/descendant-or-self::node()/b, happens to reduce to that).

Example B.73. descendant axis examples

count(descendant::*)
count(descendant::comment())
x[descendant::y]/descendant::z

The descendant axis can have surprising results when it matches nodes contained in other matched nodes. In this case, both the containing node (including all its content) and the contained node are selected. The contained node will thus appear more than once in the output (once in the selection, and once in each other selected node that contains it).

Example B.74. descendant can select nodes contained in other selected nodes

(<a><b id="1"><b id="2"/></b></a>)/descendant::b
=>
<b id="1"><b id="2"/></b><b id="2"/>

See also: Chapter 3, and // (navigation operator), attribute, child, descendant-or-self, parent, and self in this appendix.

The descendant-or-self axis matches all descendants (element, text, comment, and processing-instruction nodes) of the current context node, and also the node itself. The node test can be used to filter this selection further, for example, matching only those with a particular name or node kind. Note that the descendant-or-self axis includes the current node itself; to exclude it, use the descendant axis.

The descendant-or-self axis itself can be abbreviated using //, which actually stands for /descendant-or-self::node()/. Because this abbreviation involves multiple steps, predicates applied to the step after it may not have the meaning you expect. For example, //x selects every x element in the current document. However, //x[1] doesn't select the first x element in the current document. Instead, //x[1] expands to /descendant-or-self::node()/x[1], which first matches every node in the current document (including the document node itself) and then for each one selects the first child element named x. Depending on the document, this can result in a single x element or many. To select the first x element in the entire document, you would need to use (//x)[1].

Example B.75. descendant-or-self axis examples

count(//*)
count(//comment())
x[.//y]//z
x[descendant-or-self::node()/y]/descendant-or-self::node()/z

Like the descendant axis, the descendant-or-self axis can have surprising results when it matches nodes contained in other matched nodes. In this case, both the containing node (including all its content) and the contained node are selected. The contained node will thus appear more than once in the serialized output (once in the selection, and once in each other selected node that contains it). For example, the query in Listing B.76 selects the outer b element with id="1" followed by the inner b element with id="2". The inner element also appears a second time in the output, as the child of the outer element.

Example B.76. descendant-or-self can seem to select duplicate nodes

(<a><b id="1"><b id="2"/></b></a>)//b
=>
<b id="1"><b id="2"/></b><b id="2"/>

See also: Chapter 3; // (navigation operator); attribute, child, descendant, parent, and self in this appendix; and Chapter 11.

In XQuery, like XPath 1.0, division is expressed using the div keyword, not slash (/). Slash is used for paths.

Like all arithmetic operators, div first atomizes both operands. If either sequence of atomic values is empty, then it returns the empty sequence. If either sequence contains more than one value, then it raises an error. Otherwise, if either operand is type xdt:untypedAtomic, it is converted to xs:double. If both operands are numeric, then they are promoted to a common type (see Appendix A). No other type conversions are performed; the two operands must support division or an error is raised.

On numeric types, the result of division is always xs:double. To perform integer division, either use the idiv operator or else one of the rounding functions (floor(), ceiling(), round(), and round-to-even()).

Note that when using floating-point types, division by zero doesn't result in an error. Instead, it results in a special double value (positive infinity, negative infinity, or not-a-number).

Example B.77. Division examples

1 div 2                      => 0.5
1E0 div 2                    => 5E-1
1 div 0                      => error (: division by zero :)
1E0 div 0                    => INF
1 div xdt:untypedAtomic("2") => 5E-1
1 div "2"                    => error (: operand is not numeric :)

Division is asymmetrical. In the list below, the operand types must occur in the order given (left to right). The pairs of types that support division are:

  • Both numeric types (xs:decimal, xs:double, and xs:float, and subtypes of these). When both operands are xs:integer, div returns xs:decimal.

  • xdt:yearMonthDuration and xs:decimal (resulting in xdt:yearMonthDuration).

  • xdt:dayTimeDuration and xs:decimal (resulting in xdt:dayTimeDuration).

All others raise an error.

See also: Chapter 5; idiv, mod, * (multiplication), - (subtraction), + (addition), and / (slash) in this appendix; and the section “Atomization” in Chapter 2.

XQuery provides only one way to construct a document node in the query: The document constructor, which takes a single argument, the content of the document node.

Each item in the content sequence is processed as follows:

  • Element, processing-instruction, text, and comment nodes are deep-copied. Element nodes copied in this way are typed as xs:anyType, and attribute nodes copied in this way are typed as xs:anySimpleType, even if the originals had more specific types.

  • Sequences of atomic values are converted into text nodes as if by the text constructor (the values are converted to string and separated by spaces).

  • All other items (i.e., document and attribute nodes) result in an error.

The resulting sequence of items (possibly empty) is the content of the constructed document node. The document constructor does not enforce XML well-formedness rules (such as that the document must contain exactly one element node), although some implementations may enforce them anyway (during serialization, or before).

Example B.78. Computed document constructor examples

document { () }
document { <root>{ doc("foo.xml") } </root> }

The document constructor is most useful in situations where you want to change the schema types of nodes, or when you want to create an entire XML document (as if by the doc() function). Use the validate operator to apply more specific types to the constructed document.

See also: Chapter 7, and attribute (constructor), element (constructor), text (constructor), and validate in this appendix.

XQuery uses “scientific E-notation” to indicate that a number is a double-precision floating-point number (instead of an integer or decimal).

E notation can be written using either a lowercase or uppercase E followed by an exponent (which can be positive or negative; if no sign is provided, then the exponent is positive). The result is the number in front of the E times ten raised to the exponent power. For example, 1.0e2 is 100, while 1.0E-2 is one one-hundredth (.01).

Example B.79. E notation examples

1.0e2
1.0e+2
1.0E+2
2.34e+0
56E-2

See also: Chapter 1, and xs:double in Appendix A.

The computed element constructor takes two arguments: the name and the content. The name expression can be an ordinary name, or an expression (enclosed in curly braces) that computes the name. Elements with constant names can be constructed using the ordinary XML syntax (<name>{content}</name>), so the computed name case is the one that more commonly uses the computed element constructor.

When the name is computed, the name expression must result in either an xs:QName value or else an xs:string value, which is then parsed into a QName using the in-scope namespaces. If the name cannot be parsed or isn't a QName, then an error is raised. Otherwise, the resulting QName value is the name of the element.

Each item in the (possibly empty) content expression is handled as follows:

  • Nodes are deep-copied. Element nodes copied in this way are typed as xs:anyType, and attribute nodes copied in this way are typed as xs:anySimpleType, even if the originals had more specific types.

  • Sequences of atomic values are converted into text nodes as if by the text constructor (the values are converted to string and separated by spaces).

  • Document nodes aren't allowed in the content (resulting in an error).

  • Attribute nodes aren't allowed after any other node kinds. Attributes at the start of the content sequence become attributes of the constructed element, and an error is raised if any two of them have the same name.

The resulting sequence of items (possibly empty) is the content of the constructed element node.

Unlike the computed document constructor, the computed element constructor implicitly validates its content (and therefore also enforces XML well-formedness rules), using the current validation mode and validation context. When the element name is constant, it is added to the validation context; otherwise, the validation context is set to global. If there aren't any types in scope, then the constructed element type is xs:anyType.

Example B.80. Computed element constructor examples

element foo { () }                           => <foo/>
element { concat("a", "b") } { "c", "d", 3 } => <ab>c d 3</ab>

See also: Chapter 7, and attribute (constructor), comment (constructor), declare validation, document (constructor), namespace (constructor), pi (constructor), and text (constructor) in this appendix.

The eq operator takes two operands, which can be arbitrary expressions. It first atomizes both operands; an error is raised if the atomized operands aren't single atomic values. If either atomized operand is type xdt:untypedAtomic, then it is cast to xs:string.

Then eq returns true if the first operand is equal to the second. If the two operands aren't comparable types, then an error is raised. See Chapter 5 for details.

Example B.81. eq examples

2 eq 1.0              => false
2 eq 2.0              => true
"10" eq 2             => error
"10" eq "2"           => false (: depends on default collation :)

See also: Chapter 5; the section “Atomization” in Chapter 2; and = (equals sign), ne, is, gt, ge, lt, and le in this appendix.

The every operator performs universal quantification; that is, it tests whether every item satisfies a condition. It takes one or more variable clauses separated by commas. Each of these introduces a variable into scope for the remainder of the every expression, and causes that variable to range over some sequence. The condition expression is specified after the keyword satisfies at the end of the expression. The result is true if every variable assignment causes the condition expression to evaluate to true.

Example B.82. every examples

every $i in (1, 2, 3) satisfies $i >= 4                 => false
every $i in (1, 2, 3) satisfies $i < 4                  => true
every $i in (1, 2), $j in (3, 4) satisfies $i * $j = 10 => false
every $i in (1, 2), $j in (3, 4) satisfies $i * $j = 8  => false

The every operator can be expressed less conveniently using exists() and FLWOR. For example, every $var1 in $expr1, $var2 in $expr2, ... satisfies $condition is equivalent to the double-negated expression not(exists(for $var1 in $expr1, $var2 in $expr2, ... where not($condition) return 1)).

See also: Chapter 6, and FLOWR and some in this appendix.

The except operator takes two operands, which must be node sequences (possibly empty). It returns all the nodes that are in the first sequence but not in the second (using node identity to determine equality), and sorts the resulting node sequence by document order.

Example B.83. except example

let $a := <a/>, $b := <b/>, $c := <c/>
return ($a, $b) except ($b, $c)
=>
  $a

Unlike the set intersection and union operators, the set difference operator is asymmetric. The symmetric set difference (all the nodes that are in one of the two sets but not in both) can be computed using either of the two expressions in Listing B.84.

Example B.84. Two ways to compute the symmetric difference of two node sets $a and $b

($a except $b) union ($b except $a)
($a union $b) except ($a intersect $b)

See also: Chapter 5, and intersect and union in this appendix.

The FLWOR (“flower”) expression is the most complex, but also the most important, expression in XQuery. It is the only way to construct a sequence sorted in any order other than document order. It is also the most convenient way to introduce variables into scope or to join a sequence with others (or itself).

FLWOR uses one or more for and let clauses (in any order), an optional where clause, an optional order by clause, and a return clause. FLWOR gets its name from the first letters of these clauses (for, let, where, order by, return).

The for and let clauses construct what is known as a tuple space, which can be visualized as a matrix of columns and rows. Each variable introduced by a for or let is a column in the matrix. The where clause filters that tuple space, the order by clause sorts it, and then the return clause returns an item for each row remaining in the tuple space. The overall result is this filtered, sorted sequence of items.

for

Each for clause introduces one or more variables into scope, each iterating over sequences of zero or more items. The tuple space gets one row for each item in the cross-product of all the for clauses; consequently, if any of the for clauses iterate over an empty sequence, then the tuple space is empty. If there aren't any for clauses, then the tuple space consists of a single row.

Example B.85. for clauses iterate over sequences

for $i in (1, 2), $j in (3, 4, 5)
for $k in (6, 7)
return ($i, $j, $k)
=>
(1, 3, 6, 1, 3, 7, 1, 4, 6, 1, 4, 7, 1, 5, 6, 1, 5, 7,
 2, 3, 6, 2, 3, 7, 2, 4, 6, 2, 4, 7, 2, 5, 6, 2, 5, 7)

Each for variable may optionally introduce an additional position variable using the keyword at. Each position variable tracks the position of the for variable as it iterates through the sequence, as shown in Listing B.86.

Example B.86. Position variables track position for each for clause independently

for $i in ("a", "b", "c") at $pos
return ($i, $pos)
=>
("a", 1, "b", 2, "c", 3)

let

Each let clause introduces one or more variables into scope, binding them to values. Unlike the for clauses, the let clauses don't contribute to the rows of the tuple space.

Example B.87. let assigns variables to values instead of iterating over them

let $i := ("x", "y", "z")
return count($i)
=>
3

for $i in ("x", "y", "z")
return count($i)
=>
(1, 1, 1)

The let clause is most commonly used when an expression is used several times. However, note that variables preserve node identity, and so they aren't quite the same as writing the expression twice.

Example B.88. Variables preserve identity

let $x := <x/>   (: constructs one node :)
return $x is $x
=>
true

<x/> is <x/>     (: constructs two nodes :)
=>
false

Variables introduced using for and let clauses are in scope for all remaining expressions, including later for and let clauses, as shown in Listing B.89.

Example B.89. Variables are in scope for the rest of the FLWOR, even other for/let clauses

for $i in (1, 2, 3) at $p
let $j := $i * $p
for $k in ($i, $j)
return $k
=>
(1, 1, 2, 4, 3, 9)

where

The where clause specifies a condition expression, which is converted to a boolean value using the Effective Boolean Value rule (see Chapter 2). If no where clause is given, then the condition is always true. The condition is evaluated once for each row in the tuple space, before the order by clause is applied, and only those rows for which the condition is true are kept.

Example B.90. The where clause filters the tuple space

for $i in ("a", "b", "c", "d") at $p
where $p > 2
return $i
=>
("c", "d")

In this way, the where clause is very similar to a predicate applied to a path. The where clause is especially useful for joining two or more sequences according to some conditions, as shown in Listing B.91.

Example B.91. FLWOR is commonly used to join sequences

for $i in ("a", "b"¸ "c", "d") at $pos
for $j in (6, 3, 1, 2)
where $pos = $j
return $i
=>
"c", "a", "b"

order by

The order by clause sorts the rows of the filtered tuple space (after the where clause is applied). It takes a list of one or more sort keys, and uses these to sort the expression.

Example B.92. order by sorts the filtered tuple space

for $i in ("a", "b", "c", "d") at $p
where $p > 2
order by $p descending  (: sorting occurs after filtering :)
return $i
=>
("d", "c")

Additionally, each sort key may specify modifiers that control how it affects the sort order. These modifiers may specify a direction (ascending or descending; ascending is the default), a collation to use for sorting strings (collation "name"; the default collation is used if no other is specified), and whether empty sequences should sort first or last (empty least or empty greatest; the default is implementation-defined). The entire order by clause can also require the ordering to be stable (the default is implementation-defined). Complete explanations of these modifiers are given in Chapter 6.

return

Finally, the return clause constructs a result for each row in the filtered, sorted tuple space. If the return clause itself is a sequence, then the sequences are all combined in order and then flattened to produce a single sequence result.

Example B.93. The return clause constructs a result for each row in the tuple space

for $i in ("a", "b", "c", "d")
for $j in (4, 1, 3, 2, 4)
where $i = $j
return <x y="{$i}"/>
=>
<x y="d"/>
<x y="a"/>
<x y="c"/>
<x y="b"/>
<x y="d"/>

See also: Chapter 6; every, some, and $ (variable) in this appendix; and the section “Effective Boolean Value” in Chapter 2.

The following axis matches all nodes that are in the same document as the current context node and come after it in document order. The node test can be used to filter these nodes further, for example, matching only those with a particular name or node kind. XQuery implementations aren't required to support the following axis.

Example B.94. following axis examples

count(following::*)
x[following::y]/following::z

See also: Chapter 3, and following-sibling, preceding, preceding-sibling, >> (after), and << (before) in this appendix.

The following-sibling axis matches all siblings of the current context node that come after it in document order. XQuery implementations aren't required to support the following-sibling axis.

Example B.95. following-sibling axis examples

following-sibling::foo/bar
count(following-sibling::*)

See also: Chapter 3, and following, preceding, preceding-sibling, >> (after), and << (before) in this appendix.

The ge operator takes two operands, which can be arbitrary expressions. It first atomizes both operands; an error is raised if the atomized operands aren't single atomic values. If either atomized operand is type xdt:untypedAtomic, then it is cast to xs:string.

Then, ge returns true if the first operand is greater than or equal to the second. If the two operands aren't comparable types, then an error is raised. See Chapter 5 for details.

Example B.96. ge examples

2 ge 1.0              => true
2 ge 2.0              => true
"10" ge 2             => error
"10" ge "2"           => false (: depends on default collation :)

See also: Chapter 5; the section “Atomization” in Chapter 2; and >= (greater than or equal to), gt, lt, le, eq, and ne in this appendix.

The gt operator takes two operands, which can be arbitrary expressions. It first atomizes both operands; an error is raised if the atomized operands aren't single atomic values. If either atomized operand is type xdt:untypedAtomic, then it is cast to xs:string.

Then gt returns true if the first operand is greater than the second. If the two operands aren't comparable types, then an error is raised. See Chapter 5 for details.

Example B.97. gt examples

2 gt 1.0              => true
2 gt 2.0              => false
"10" gt 2             => error
"10" gt "2"           => false (: depends on default collation :)

See also: Chapter 5; the section “Atomization” in Chapter 2; and > (greater-than sign), ge, lt, le, eq, and ne in this appendix.

The idiv operator performs integer division on two integer values. Like all arithmetic operators, idiv first atomizes both operands. If either sequence of atomic values is empty, then it returns the empty sequence. If either sequence contains more than one value, then it raises an error.

Otherwise, if either operand is type xdt:untypedAtomic, it is converted to xs:integer. No other type conversions are performed; the two operands must both be xs:integer (or a subtype of it) or else an error is raised.

Example B.98. Integer division examples

1 idiv 2                      => 0
1E0 idiv 2                    => error (: operand not integer :)
1 idiv 0                      => error (: division by zero :)
1 idiv xdt:untypedAtomic("2") => 0
1 idiv "2"                    => error (: operand not integer :)

See also: Chapter 5; div, mod, * (multiplication), - (subtraction), + (addition), and / (slash) in this appendix; the section “Atomization” in Chapter 2; and fn:round() in Appendix C.

The if operator takes a conditional expression (in parentheses) and two branch expressions. If the condition is true, then the first branch (then) is the result; if the condition is false, then the second branch (else) is the result.

The condition can be any expression at all; if converts it to a boolean value by applying the Effective Boolean Value rule.

Example B.99. if examples

if (true()) then "1" else 1.0          => "1"
if (1 < 2 and 2 < 3) then "x" else "y" => "x"

Conditionals can be chained together one after another, as shown in Listing B.100, but a final else branch is always required.

Example B.100. Conditionals can be chained together

if ($x) then 1
else if ($y) then 2
else if ($z) then 3
else 0

See also: Chapter 5; the section “Effective Boolean Value” in Chapter 2; and FLWOR, typeswitch, and [ (left square bracket) in this appendix.

A module import includes all the functions and variables defined in another module (the target module) into the current one (the source module). All other definitions, such as namespace declarations, are not imported. Modules may import any number of other modules.

Each module import names the target namespace of the target module; the namespace must be a string literal. Optionally, a module import may assign a namespace prefix to this namespace (with the same effect as declare namespace) and/or may provide a location hint to the implementation. The location hint must be a string literal.

Each module has its own independent static context. If any of the imported functions or variables already exists in the source module, an error is raised. When the target module is imported, none of the modules that it has imported are imported with it. (For example, if module X imports module Y, and module Y imports module Z, then module X has not imported module Z without a separate import module statement.)

Moreover, all of the “public” types—that is, the return type and parameter types of functions, and the types of global variables—that are used by the target module must be already available in the source module. For example, if X imports module Y, and Y has a function that uses type T as its return type or a parameter type, or has a global variable of type T, then T must be already defined in X.

Example B.101. import module examples

import module "urn:foo";
import module x = "urn:bar";

See also: The section “Query Prolog” in Chapter 5, the section “Modules” in Chapter 4, and module in this appendix.

The import schema prolog instruction has several different forms. The most basic one takes a string argument that specifies the target namespace of the schema; the implementation must know how to locate the given schema. Optionally, you may also specify the schema location (which may be ignored by the implementation). The effect is to load those schema types into the given target namespace.

The most common use of import schema is to accomplish two tasks at once: declare a namespace prefix and import the schema for that namespace. This is done by writing import schema prefix = namespace (and again optionally specifying a schema location, which may be ignored by the implementation). To use the namespace as the default element namespace, use the keywords default element namespace instead of a prefix. These different forms are illustrated in Listing B.102.

Example B.102. import schema examples

import schema "urn:foo";
import schema "urn:foo" at "http://www.w3c.org/foo.xsd";
import schema x = "urn:foo" at "http://www.w3c.org/foo.xsd";
import schema default element namespace "urn:foo";

See also: The section “Query Prolog” in Chapter 5, the section “Validation” in Chapter 9, and validate in this appendix.

The instance of operator takes an expression and a sequence type, and performs sequence type matching. If the value matches the type, then instance of returns true, otherwise it returns false.

Example B.103. instance of examples

<x/> instance of element()        => true
<x/> instance of xs:integer       => false
(1, 2, 3) instance of xs:integer* => true
() instance of xs:integer*        => true
() instance of xs:integer+        => false

See also: Chapter 9; castable as, treat as, and typeswitch in this appendix; and the section “Sequence Type Matching” in Chapter 2.

The intersect operator takes two operands, which must be node sequences (possibly empty). It returns all the nodes that are in both sequences (using node identity to determine equality), and returns the resulting node sequence sorted in document order.

Example B.104. intersect examples

let $a := <a/>, $b := <b/>, $c := <c/>
return ($a, $b) intersect ($b, $c)
=>
  $b

See also: Chapter 5, and except and union in this appendix.

The node comparison operator is takes two operands, each of which must be either a single node or the empty sequence or else a type error is raised. If either operand is empty, then is returns the empty sequence. Otherwise, is returns true if the two nodes are the same (by identity) and otherwise false.

Example B.105. is examples

() is ()                         => ()
doc("foo.xml") is doc("foo.xml") => true
<x/> is <x/>                     => false
let $x := <x/> return $x is $x   => true

See also: Chapter 5 and fn:deep-equal() in Appendix C.

The le operator takes two operands, which can be arbitrary expressions. It first atomizes both operands; an error is raised if the atomized operands aren't single atomic values. If either atomized operand is type xdt:untypedAtomic, then it is cast to xs:string.

Then le returns true if the first operand is less than or equal to the second. If the two operands aren't comparable types, then an error is raised. See Chapter 5 for details.

Example B.106. le examples

2 le 1.0              => false
2 le 2.0              => true
"10" le 2             => error
"10" le "2"           => true (: depends on default collation :)

See also: Chapter 5; the section “Atomization” in Chapter 2; and <= (less than or equal to), ge, gt, lt, eq, and ne in this appendix.

The lt operator takes two operands, which can be arbitrary expressions. It first atomizes both operands; an error is raised if the atomized operands aren't single atomic values. If either atomized operand is type xdt:untypedAtomic, then it is cast to xs:string.

Then, lt returns true if the first operand is less than the second. If the two operands aren't comparable types, then an error is raised. See Chapter 5 for details.

Example B.107. lt examples

2 lt 1.0              => false
2 lt 2.0              => false
"10" lt 2             => error
"10" lt "2"           => true (: depends on default collation :)

See also: Chapter 5; the section “Atomization” in Chapter 2; and < (less than sign), ge, gt, le, eq, and ne in this appendix.

The mod operator performs modulo arithmetic on two numbers. Like all arithmetic operators, mod first atomizes both operands. If either sequence of atomic values is empty, then it returns the empty sequence. If either sequence contains more than one value, then it raises an error.

Otherwise, mod performs truncating division and returns the remainder. The sign of the result is the same as the sign of the left expression.

Formally, the expression lhs mod rhs returns the value x such that (lhs tdiv rhs)*rhs + x equals lhs and the absolute value of x is less than the absolute value of rhs, where tdiv means truncating division (truncating the result to an integer value). If either operand is NaN, or if the left expression is infinite or the right expression is zero, then the result is NaN. Otherwise, if the right expression is infinite then the result is the left expression is unchanged.

Example B.108. mod examples

4 mod 3                      => 1
4 mod 3.0                    => 1.0
4E0 mod 3                    => 1E0
4E0 mod 0                    => NaN
4 mod xdt:untypedAtomic("3") => 1E0
4 mod "3"                    => error (: operand not numeric :)

See also: Chapter 5; div, idiv, * (multiplication) , + (addition) , and - (subtraction) in this appendix; and the section “Atomization” in Chapter 2.

The module declaration indicates that a query is a library module (instead of the main module). Library modules aren't evaluated directly, but may define functions and variables for other modules to use. The module declaration is mutually exclusive with the query body; a query can have one but not the other.

The module declaration requires a prefix and namespace (which must be a string literal). This is the target namespace of the module, and also its default function namespace. All variables and functions defined in the module must belong to this namespace, or else an error is raised.

Library modules may import other library modules using import module.

Example B.109. module example

module namespace foo = "urn:bar";

See also: The section “Query Prolog” in Chapter 5, the section “Modules” in Chapter 4, and import module in this appendix.

The computed namespace constructor takes a prefix (which cannot be computed) and an enclosed expression, which is computed to produce the namespace uri. It constructs a namespace node binding the prefix to that namespace.

The content expression is processed the same as with the computed comment constructor: First, it is first atomized. If the resulting sequence is empty, then the content is the empty string. Otherwise, each atomic value is cast to xs:string, concatenated together with a space character in between each consecutive pair, and the final result becomes the namespace value.

Computed namespace nodes can be used only in element constructors (computed or direct).

Example B.110. Computed namespace constructor example

namespace foo { "urn:bar" }  => xmlns:foo="urn:bar"

See also: Chapter 7, and attribute (constructor), comment (constructor), document (constructor), element (constructor), pi (constructor), and text (constructor) in this appendix.

The ne operator takes two operands, which can be arbitrary expressions. It first atomizes both operands; an error is raised if the atomized operands aren't single atomic values. If either atomized operand is type xdt:untypedAtomic, then it is cast to xs:string.

Then ne returns true if the first operand is not equal to the second. If the two operands aren't comparable types, then an error is raised. See Chapter 5 for details.

Example B.111. ne examples

2 ne 1.0              => true
2 ne 2.0              => false
"10" ne 2             => error
"10" ne "2"           => true (: depends on default collation :)

See also: Chapter 5, the section “Atomization” in Chapter 2, and != (inequality sign), eq, ge, gt, le, and lt in this appendix.

The or operator first converts both of its operands to boolean using the fn:boolean() function (Effective Boolean Value). If either operand is true, then or returns true, otherwise it returns false.

Example B.112. or examples

true() or false()        => true
"" or 0.0                => false
"x" or 1.0               => true
() or (false(), false()) => true

The order in which the or operator evaluates its arguments is implementation-dependent, and implementations are also allowed (and encouraged) to “short-circuit” this operator (evaluating only one of its operands if that is enough to determine the overall result). Consequently, expressions like error() or true() and true() or error() may raise an error or may return true, depending on the implementation.

See also: Chapter 5, and in this appendix, and fn:boolean()and fn:not() in Appendix C.

The parent axis selects the parent node of the current context node (if it has a parent; the root document or element node does not, in which case the parent axis is empty). The node test can be used to filter the parent further, for example, matching only those with a particular name or node kind.

It's common practice to abbreviate the parent axis with two periods (..), like file systems use to navigate to the parent directory. The abbreviation expands to parent::node().

Example B.113. parent axis examples

count(parent::node())
x/parent::node()
x/..

See also: Chapter 3, and .. (parent navigation), . (dot), attribute, child, descendant, descendant-or-self, and self in this appendix.

Example B.114. Computed processing instruction constructor examples

processing-instruction { "foo" }           => <? foo?>
processing-instruction { "foo" } { "bar" } => <?foo bar?>

See also: Chapter 7, and attribute (constructor), comment (constructor), document (constructor), element (constructor), namespace (constructor), and text (constructor) in this appendix.

The preceding axis matches all nodes in the same document as the current context node and comes before it in document order. The node test can be used to filter these nodes further, for example, matching only those with a particular name or node kind. XQuery implementations aren't required to support the preceding axis.

Example B.115. preceding axis examples

count(preceding::*)
x[preceding::y]/preceding::z

See also: Chapter 3, and following, following-sibling, preceding-sibling, >> (after), and << (before) in this appendix.

The preceding-sibling axis matches all siblings of the current context node that come before it in document order. XQuery implementations aren't required to support the preceding-sibling axis.

Example B.116. preceding-sibling axis examples

preceding-sibling::foo/bar
count(preceding-sibling::*)

See also: Chapter 3, and following, following-sibling, preceding, >> (after), and << (before) in this appendix.

The computed processing instruction constructor takes one or two enclosed expressions, and uses them to construct a processing instruction node. If two expressions are given, then the first one is used to compute the processing instruction target. The other expression is the string content of the processing instruction.

The name expression, if any, must either return a qualified name (xs:QName) or a string that can be converted to xs:QName.

The content expression is processed the same as with the computed comment constructor: First, the value is first atomized. If the resulting sequence is empty, then the content is the empty string. Otherwise, each atomic value is cast to xs:string, concatenated together with a space character in between each consecutive pair, to produce the final content result.

The self axis selects the current context node. The node test can be used to filter the context node, for example, matching only those with a particular name or node kind.

It's common practice to abbreviate the self axis with one period (.), like file systems use to navigate to the current directory. In XPath 1.0, this abbreviation expands to self::node(); however, in XQuery, . selects the current context item (which may or may not be a node).

At first glance, the self axis may appear useless, but actually it is very helpful in predicates, where it can be used to navigate relative to the current context node, or access its value. It is also sometimes useful for testing the node kind or the name of the current context node.

Example B.117. self axis examples

x[.//y] (: .//y is a relative path, starting from the current node :)
x[//y]  (: //y is an absolute path, starting from the root :)
x[data(.) = 1]
self::comment()

See also: Chapter 3, and . (current context item), attribute, child, descendant, descendant-or-self, and parent in this appendix.

The some operator performs existential quantification; that is, it tests whether there exists an item satisfying a condition. It takes one or more variable clauses separated by commas. Each of these introduces a variable into scope for the remainder of the some expression, and causes that variable to range over some sequence. The condition expression is specified after the keyword satisfies at the end of the expression. The existence test checks whether there exists an assignment to all the variables such that the condition is true.

Example B.118. some examples

some $i in (1, 2, 3) satisfies $i >= 4                 => false
some $i in (1, 2, 3) satisfies $i < 4                  => true
some $i in (1, 2), $j in (3, 4) satisfies $i * $j = 10 => false
some $i in (1, 2), $j in (3, 4) satisfies $i * $j = 8  => true

The some operator can be expressed less conveniently using exists() and FLWOR. For example, some $var1 in $expr1, $var2 in $expr2, ... satisfies $condition is equivalent to the expression exists(for $var1 in $expr1, $var2 in $expr2, ... where $condition return 1).

See also: Chapter 6, and FLWOR and every in this appendix.

The text constructor takes an optional argument, which is the content of the text node. It first atomizes the content. If the sequence is empty (or if the argument is omitted), then no text node is constructed and the result is the empty sequence. Otherwise, each atomic value is converted to string as if by using the cast as operator, and concatenated together by inserting spaces in between them. The resulting string value (which may be empty) is the content of the computed text node.

In other words, the expression text { $X } is equivalent to the much lengthier expression in Listing B.119

Example B.119. An expression equivalent to text { $X }

if (empty($X)) then ()
else text { string-join(" ", for $i in data($X) return string($i) }

The text constructor is most useful in situations where you want absolute control over how XML is constructed, such as mixed-content elements. The text constructor can also be used to construct text nodes without an enclosing element.

Example B.120. Computed text constructor examples

text { }                        => ()
text { () }                     => ()
text { 1, 2, 3 }                => text { "1 2 3" }
<x>{ <y/>, text { "zzz" } }</x> => <x><y/>zzz</x>

See also: Chapter 7, and attribute (constructor), document (constructor), and element (constructor) in this appendix.

The range operator to takes two arguments, each of which is converted to xs:integer using function conversion rules (raising a conversion error if necessary).

The range operator then constructs the sequence of integers between the two arguments, inclusive. If the first argument is less than the second, then the sequence is increasing. If the first argument is greater than the second, then the sequence is empty. If the first argument is equal to the second, then the sequence contains only the one integer value.

Example B.121. to examples

1 to 3 => (1, 2, 3)
3 to 1 => ()
3 to 3 => 3
xdt:untypedAtomic("-1") to xs:long(2) => (-1, 0, 1, 2)

See also: Chapter 5, and the section “Function Conversion Rules” in Chapter 4.

The treat as operator takes two arguments: an expression and a sequence type. If the expression value is an instance of the given type, then treat as returns the value unchanged; otherwise, an error is raised.

In other words, treat as is just a way to ensure that an expression has the correct static type. Unlike the cast as operator, treat as doesn't change the value or its type. In some languages, this is known as down-casting.

Example B.122. treat as examples

2 treat as xs:decimal   => 2
2.0 treat as xs:integer => error

2 cast as xs:decimal    => 2.0
2.0 cast as xs:integer  => 2

See also: Chapter 9, cast as and instance of in this appendix, and the section “Sequence Type Matching” in Chapter 2.

The typeswitch operator takes an expression and then chooses the first case that matches its type (or the default branch if there isn't a match). The sequence type matching process is described in Appendix A.

Each case (including the default one) may optionally introduce a variable, which is bound to the original expression but more strongly typed using the type named in the case (in the default case, the variable's static type is the same as that of the original expression). The variable is in scope for the clause of that case only; multiple cases may use the same variable name.

Note that typeswitch requires at least one case and exactly one default branch. Also, don't forget that the comma operator has lower precedence than typeswitch, so the default case return clause must use parentheses to return a sequence of expressions.

Example B.123. typeswitch examples

typeswitch (<hello/>)
  case $a as attribute return concat("a:", local-name($a))
  case $e as element return concat("e:", local-name($e))
  default return "x"
=>
"e:hello"

for $i in (1, <x/>, "2")
return typeswitch ($i)
         case xs:integer return "integer"
         case xs:decimal return "decimal"
         case xs:string  return "string"
         case node()     return "node"
         default         return error("unknown type")
=>
("integer", "node", "string")

The typeswitch operator is useful whenever you need to perform different actions for different item kinds, node kinds, or atomic types. For example, you can write a function that computes the built-in XQuery type name of an expression (see Listing B.124). The first matching case is used, so the order of the case clauses matters. In general, when using typeswitch, list subtypes first.

Example B.124. A user-defined function for computing sequence type names

declare function sequence-type-of($expr) as xs:string {
    if (count($expr) > 1) then concat(single-type-of($expr), "+")
    else single-type-of($expr)
};

declare function single-type-of($expr) as xs:string {
    typeswitch ($expr)
        case empty()                   return "empty()"
        case element()*                return "element()"
        case attribute()*              return "attribute()"
        case text()*                   return "text()"
        case comment()*                return "comment()"
        case document-node()*          return "document-node()"
        case processing-instruction()* return "processing-instruction()"
        case node()*                   return "node()"
        case xdt:untypedAtomic*        return "xdt:untypedAtomic"
        case xs:unsignedByte*          return "xs:unsignedByte"
        case xs:unsignedShort*         return "xs:unsignedShort"
        case xs:unsignedInt*           return "xs:unsignedInt"
        case xs:unsignedLong*          return "xs:unsignedLong"
        case xs:positiveInteger*       return "xs:positiveInteger"
        case xs:nonNegativeInteger*    return "xs:nonNegativeInteger"
        case xs:byte*                  return "xs:byte"
        case xs:short*                 return "xs:short"
        case xs:int*                   return "xs:int"
        case xs:long*                  return "xs:long"
        case xs:negativeInteger*       return "xs:negativeInteger"
        case xs:nonPositiveInteger*    return "xs:nonPositiveInteger"
        case xs:integer*               return "xs:integer"
        case xs:decimal*               return "xs:decimal"
        case xs:ENTITY*                return "xs:ENTITY"
        case xs:IDREF*                 return "xs:IDREF"
        case xs:ID*                    return "xs:ID"
        case xs:NCName*                return "xs:NCName"
        case xs:Name*                  return "xs:Name"
        case xs:NMTOKEN*               return "xs:NMTOKEN"
        case xs:language*              return "xs:language"
        case xs:token*                 return "xs:token"
        case xs:normalizedString*      return "xs:normalizedString"
        case xs:string*                return "xs:string"
        case xdt:dayTimeDuration*      return "xdt:dayTimeDuration"
        case xdt:yearMonthDuration*    return "xdt:yearMonthDuration"
        case xs:duration*              return "xs:duration"
        case xs:NOTATION*              return "xs:NOTATION"
        case xs:QName*                 return "xs:QName"
        case xs:anyURI*                return "xs:anyURI"
        case xs:double*                return "xs:double"
        case xs:float*                 return "xs:float"
        case xs:hexBinary*             return "xs:hexBinary"
        case xs:base64Binary*          return "xs:base64Binary"
        case xs:boolean*               return "xs:boolean"
        case xs:date*                  return "xs:date"
        case xs:time*                  return "xs:time"
        case xs:dateTime*              return "xs:dateTime"
        case xs:gMonth*                return "xs:gMonth"
        case xs:gDay*                  return "xs:gDay"
        case xs:gMonthDay*             return "xs:gMonthDay"
        case xs:gYear*                 return "xs:gYear"
        case xs:gYearMonth*            return "xs:gYearMonth"
        case xdt:anyAtomicType*        return "xdt:anyAtomicType"
        case xs:anySimpleType*         return "xs:anySimpleType"
        case xs:anyType*               return "xs:anyType"
        default                        return "item()"
};

See also: Chapter 9; Appendix A; fn:data() in Appendix C, and cast as, if, instance of, and validate in this appendix.

The union operator takes two operands, both of which must be node sequences (possibly empty). It combines both sequences, removes duplicate nodes (by node identity), and sorts the result in document order. The union operator can also be written as | (the vertical bar).

Example B.125. union examples

let $a := <a/>, $b := <b/>, $c := <c/>
return ($a, $b) union ($b, $c)
=>
  ($a, $b, $c)


() | () => ()

See also: Chapter 5, and except and intersect in this appendix.

The validate operator specifies an optional schema mode, which must be either lax, skip, or strict. If the mode is omitted, then the default validation mode is used. (The default validation mode can be set using the declare validation declaration in the schema prolog.) The mode used becomes the default validation mode for all nested expressions.

The validate operator also specifies an optional schema context, which must be one of the following expressions: global, type(qname), or a simple path starting with either a qname or type(qname) and followed by one or more /qname steps. If the context is omitted, then it defaults to global. The context used becomes the default validation context for all nested expressions.

The validate operator takes one operand, which is the expression to be validated (enclosed in curly braces). The expression must evaluate to exactly one document or element node.

The result of the validate expression is either the result of converting the operand into an XML Infoset, validating that infoset, and converting the validated result back into the XQuery Data Model, or else a type error (if the operand cannot be converted into a well-formed XML Infoset, or if a validation error occurs).

Example B.126. validate examples

validate { <x>12</x> }
validate strict { <x>12</x> }
validate strict type(y)/z { <x>12</x> }

See also: Chapter 9; cast as, declare validation, and typeswitch in this appendix; and Appendix A.

The version declaration, if used, must appear before all the rest of the prolog. It takes one string argument, which is the version string. If omitted, the version defaults to the string value “1.0”. An XQuery compiler must raise an error if the version string isn't supported by it.

The purpose of the version declaration is to provide a mechanism for compatibility with potential future versions of XQuery.

Example B.127. xquery version example

xquery version "1.0";
..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
18.188.40.207