<?xml version="1.0" encoding="iso-8859-1"?>
<?xml-stylesheet href="../../make-menu.xsl" type="text/xsl"?><html>
   <head>
      <this-is section="sourcedocs" page="streaming" subpage="burst-mode-streaming"/>
      <!--
           Generated at 2010-10-29T18:20:48.427+01:00--><title>Saxonica: XSLT and XQuery Processing: Burst-mode streaming</title>
      <meta name="coverage" content="Worldwide"/>
      <meta name="copyright" content="Copyright Saxonica Ltd"/>
      <meta name="title"
            content="Saxonica: XSLT and XQuery Processing: Burst-mode streaming"/>
      <meta name="robots" content="noindex,nofollow"/>
      <link rel="stylesheet" href="../../saxondocs.css" type="text/css"/>
   </head>
   <body class="main">
      <h1>Burst-mode streaming</h1>
      <p>The <code>saxon:stream</code> extension function enables burst-mode streaming by reading a source document and delivering
         a sequence of element nodes representing selected elements within that document. For example:</p>
      <div class="codeblock"
           style="border: solid thin; background-color: #B1CCC7; padding: 2px">
         <pre>
            <code>saxon:stream(doc('employees.xml')/*/employee)</code>
         </pre>
      </div>
      <p>This example returns a sequence of <code>employee</code> elements. These elements are parentless, so it is not
         possible to navigate from one employee element to others in the file; in fact, only one of them actually exists in memory
         at any one time.</p>
      <p>The function <code>saxon:stream</code> may be regarded as a pseudo-function. Conceptually, it takes the set of nodes
               supplied in its argument, and makes a deep copy of each one (the copy operation is needed to make the
               <code>employee</code> elements parentless). The resulting sequence of nodes will usually be processed by
               an instruction such as <code>xsl:for-each</code> or <code>xsl:iterate</code>, or by a FLWOR expression in XQuery,
               which handles the nodes one at a time. The actual implementation of <code>saxon:stream</code>, however, is
               rather different, in that it changes the way in which its argument is evaluated: instead of the <code>doc()</code>
               function building a tree in the normal way, the path expression <code>doc('employees.xml')/*/employee)</code>
               is evaluated in streamed mode - which means that it must conform to a subset of the XPath syntax which Saxon
               can evaluate in streamed mode. For details of this subset, see <a class="bodylink" href="../../sourcedocs/streaming/streamable-xpath.xml"/></p>
      <p>The facility should not be used if the source document is read more than once in the course
                  of the query/transformation. There are two reasons for this: firstly, performance will be better in this case if the
                  document is read into memory; and secondly, when this optimization is used, there is no guarantee that the
                  <code>doc()</code> function will be stable, that is, that it will return the same results when called
                  repeatedly with the same URI.</p>
      <p>If the path expression cannot be evaluated in streaming mode, execution does not fail; rather it is evaluated
                  with an unoptimized copy-of instruction. This will give the same results provided enough memory is available for
                  this mode of evaluation. To check whether streamed processing is actually being used, set the -t option from the
            command line or the <code>FeatureKeys.TIMING</code> option from the configuration API; the output will indicate whether
            a particular source document has been processed by building a tree, or by streaming.</p>
      <p>In XSLT an alternative way of invoking the facility is by using an <code>&lt;xsl:copy-of&gt;</code>
instruction with the special attribute <code>saxon:read-once="yes"</code>. Typically the <code>xsl:copy-of</code>
         instruction will form the body of a stylesheet function, which can then be called in the same way
         as <code>saxon:stream</code> to deliver the stream of records. This approach has the advantage that the
         code is portable to other XSLT processors (<code>saxon:read-once="yes"</code> is an extension attribute,
         a processing hint that other XSLT processors are required to ignore.)</p>
      <p>In XQuery the same effect can
be achieved using a pragma <code>(# saxon:read-once #)</code>. Again, processors other than Saxon are required to ignore this
pragma.</p>
      <p class="subhead">Example: selective copying</p>
      <p>A very simple way of using this technique is when making a selective copy of parts of a document. 
For example, the following code
creates an output document containing all the <code>footnote</code> elements from the source document
that have the attribute <code>@type='endnote'</code>:</p>
      <p><b>XSLT example</b></p>
      <div class="codeblock"
           style="border: solid thin; background-color: #B1CCC7; padding: 2px">
         <pre>
            <code>
&lt;xsl:template name="main"&gt;
  &lt;footnotes&gt;
    &lt;xsl:sequence select="saxon:stream(doc('thesis.xml')//footnote[@type='endnote'])"
                  xmlns:saxon="http://saxon.sf.net/"/&gt;
  &lt;/footnotes&gt;
&lt;/xsl:template&gt;
</code>
         </pre>
      </div>
      <p><b>XQuery example</b></p>
      <div class="codeblock"
           style="border: solid thin; background-color: #B1CCC7; padding: 2px">
         <pre>
            <code>
  &lt;footnotes&gt;{
     saxon:stream(doc('thesis.xml')//footnote[@type='endnote']) 
  }&lt;/footnotes&gt;
  </code>
         </pre>
      </div>
      <p class="subhead">XSLT example using xsl:copy-of</p>
      <p>To allow code to be written in a way that will still work with processors other than Saxon,
the facility can also be invoked using extension attributes in XSLT. Using this
syntax, the previous example can be written as:</p>
      <p><b>XSLT example</b></p>
      <div class="codeblock"
           style="border: solid thin; background-color: #B1CCC7; padding: 2px">
         <pre>
            <code>
&lt;xsl:template name="main"&gt;
  &lt;footnotes&gt;
    &lt;xsl:copy-of select="doc('thesis.xml')//footnote[@type='endnote']"
                   saxon:read-once="yes" xmlns:saxon="http://saxon.sf.net/"/&gt;
  &lt;/footnotes&gt;
&lt;/xsl:template&gt;
</code>
         </pre>
      </div>
      <p class="subhead">XQuery example using the saxon:stream pragma</p>
      <p>In XQuery the pragma <code>saxon:stream</code> is available as an alternative to the
         function of the same name, allowing the code to be kept portable. The above example can
         be written:</p>
      <div class="codeblock"
           style="border: solid thin; background-color: #B1CCC7; padding: 2px">
         <pre>
            <code>
  &lt;footnotes&gt;{
    (# saxon:stream #) {
       doc('thesis.xml')//footnote[@type='endnote']
    }   
  }&lt;/footnotes&gt;
</code>
         </pre>
      </div>
      <p>Note the restrictions below on the kind of predicate that may be used.</p>
      <table width="100%">
         <tr>
            <td>
               <p align="right"><a class="nav" href="furtherprocessing.xml">Next</a></p>
            </td>
         </tr>
      </table>
   </body>
</html>