RE: [xsl] The output of evaluating an XSLT transform is the same regardless of the order in which output elements are evaluated. Right?

Subject: RE: [xsl] The output of evaluating an XSLT transform is the same regardless of the order in which output elements are evaluated. Right?
From: "Michael Kay" <mike@xxxxxxxxxxxx>
Date: Fri, 16 Apr 2010 22:04:33 +0100
> EXAMPLES OF SEQUENTIAL ORDERING DUE TO THE XSLT SPECIFICATION
> 
>    EXAMPLE #1
> 
> In an <xsl:choose> element the first <xsl:when> element must 
> be evaluated before the following <xsl:when> elements and the 
> <xsl:otherwise> element, if present.
> 
>    <xsl:choose>
>       <xsl:when test="evaluate me first">
>         ...
>       </xsl:when>
>       <xsl:when test="evaluate me second (if the first test failed)">
>         ...
>       </xsl:when>
>    </xsl:choose>

No. The processor only has to deliver the same result *as if* it were
evaluated in that order. For example, if the conditions are

<xsl:when test="f:something() = 1">
   ...
</xsl:when>
<xsl:when test="f:something() = 5">
   ...
</xsl:when>
<xsl:when test="f:something() = 7">
   ...
</xsl:when>

then Saxon-EE will evaluate f:something() once, before entry to the
xsl:choose, and will then use a hash table to decide which branch to take.
It won't actually evaluate any of the test expressions directly at all. Of
course Saxon has to take great care with this optimization, for example if
two of the test conditions are the same, or if dynamic errors occur, so that
you can't tell that it is using a different algorithm from that described in
the specification.
> 
> EXAMPLES OF SEQUENTIAL ORDERING DUE TO LOGICAL DEPENDENCIES 
> OF CONSTRUCTS IN THE XSLT CODE
> 
>    EXAMPLE #1
> 
> A variable can be used only _after_ it's been initialized, e.g.,
> 
>    <xsl:variable name="number" select="ex:Square(4)" />
> 
>    <xsl:value-of select="$number" />
> 
> The <xsl:value-of> element must be evaluated only _after_ the 
> <xsl:variable> element has been evaluated.

Again, there are caveats. For example xsl:value-of could output something
that causes "just-in-time" evaluation of ex:Square(4). Or sometimes there
appears to be a dependency but isn't:

<xsl:variable name="number" select="ex:Square(4)" />
<xsl:if test="exists($number)">

If the return type of ex:Square is declared as xs:integer, then the
optimizer knows that exists() will return true without actually evaluating
ex:Square(4) at all.


> 
> 
>    EXAMPLE #2
> 
> In this example the sum() function must be evaluated before 
> the multiplication occurs:
> 
>    <xsl:value-of select="sum(Cost) * 1.2" />
> 
> 

Again, an optimizer could rewrite this as

sum(for $x in Cost return $x * 1.2)

I don't think it would, but it could.

Regards,

Michael Kay
http://www.saxonica.com/
http://twitter.com/michaelhkay 

Current Thread