[XSL-LIST Mailing List Archive Home] [By Thread] [By Date] [Recent Entries] [Reply To This Message]

RE: Using the Input Document to Control Generation of

Subject: RE: Using the Input Document to Control Generation of Numbers in the Output
From: "Kerry, Richard" <richard.kerry@xxxxxxxxxxx>
Date: Tue, 2 Oct 2007 16:33:39 +0100
RE:  Using the Input Document to Control Generation of
Thank you both for your various solutions, and to George for the
detailed explanation of his non-recursive solutions.

I had wondered about the "(@size, 1)[1]" term, which I'd not seen before
but I think I have now worked out.  If there is no "size" attribute, the
term "@size" returns null and thus does not appear as a first node in
the node-set, ie what's within the (), and thus [1] returns what appears
to be the second element, the '1'.

Given that I understand the recursive solution better, and I can easily
extend it to do both size and index overrides together I'm going with
that for the moment.  If I get stack problems I'll need to re-implement
it using the non-recursive method.

My xsl, now doing both overrides, is listed below.

Appreciatively,
Richard.



<!-- The incoming size attribute is the size of this element so doesn't
affect its index but affects all following.
	 The incoming index attribute affects this outgoing one and all
following.   -->

<xsl:template match="incoming">
  <xsl:param name="given-index"/>
  <!-- Use inputted index here unless overridden. -->
  <xsl:variable name="this-index" select="(@index, $given-index)[1]"/>
  <outgoing name="{@name}" index="{$this-index}"/>;
  <!-- Calculate the new index to pass into the next pass. -->
  <xsl:variable name="next-index" select="$this-index + (@size, 1)[1]"/>
  <xsl:apply-templates select="following-sibling::incoming[1]">
    <xsl:with-param name="given-index" select="$next-index"/>
  </xsl:apply-templates>
</xsl:template>

<!-- and then fire the process off with -->

<xsl:template match="parent">
  <xsl:apply-templates select="incoming[1]">
    <xsl:with-param name="given-index" select="1"/>
  </xsl:apply-templates>
</xsl:template>






-----Original Message-----
From: George Cristian Bina [mailto:george@xxxxxxxxxxxxx]
Sent: 02 October 2007 15:42
To: xsl-list@xxxxxxxxxxxxxxxxxxxxxx
Subject: Re:  Using the Input Document to Control Generation of
Numbers in the Output

Hi Richard,

Kerry, Richard wrote:
[...]
> Since I wrote the above I've received George's solution for problem 3,
> which I don't yet understand.


  <one:one xmlns:one="http://www.example.com/one" index="1"/>

Adds an element in a namespace different than the XSLT namespace, just
to be selected by the variable below.

  <xsl:variable name="one" select="document('')/*/one:one"
xmlns:one="http://www.example.com/one"/>

The one variable points to the one:one element above, I need that below
to get the default value 1 in case no previous index is found.

  <xsl:template match="incoming">

We are on an incoming element.

   <xsl:choose>
    <xsl:when test="@index">

If that specifies an index then we just use it.

     <ougoing name="{@name}" index="{@index}"/>
    </xsl:when>
    <xsl:otherwise>

otherwise we count

     <outgoing name="{@name}" index="{count(preceding-sibling::*) +

preceding siblings

      (preceding-sibling::*[@index][1]/@index|$one/@index)[1] -
the index value of the first preceding sibling that has an index
attribute or, if there is no preceding sibling with an index attribute
we use the index from the one variable, that means the value 1

      count(preceding-sibling::*[@index][1]/preceding-sibling::*)

and we remove the preceding elements after the first element that has an

index as we added all the preceding elements in the first count above

      }"/>



    </xsl:otherwise>
   </xsl:choose>

For a large number of elements you may end out of stack with a recursive

approach unless the processor optimizes that.

In case you are not using XSLT 2.0 then you need to solve
(@size, 1)[1]
from Mike's code with something like the one:one approach from my
example:

  <one:one xmlns:one="http://www.example.com/one">1</one:one>
  <xsl:variable name="one" select="document('')/*/one:one"
xmlns:one="http://www.example.com/one"/>


  <xsl:template match="incoming">
   <xsl:param name="total-so-far"/>
   <xsl:variable name="new-total" select="$total-so-far + (@size |
$one)[1]"/>;
   <outgoing name="{@name}" index="{$new-total}"/>
   <xsl:apply-templates select="following-sibling::incoming[1]">
    <xsl:with-param name="total-so-far" select="$new-total"/>
   </xsl:apply-templates>
  </xsl:template>

Best Regards,
George
---------------------------------------------------------------------
George Cristian Bina - http://aboutxml.blogspot.com/
<oXygen/> XML Editor, Schema Editor and XSLT Editor/Debugger
http://www.oxygenxml.com

Current Thread

PURCHASE STYLUS STUDIO ONLINE TODAY!

Purchasing Stylus Studio from our online shop is Easy, Secure and Value Priced!

Buy Stylus Studio Now

Download The World's Best XML IDE!

Accelerate XML development with our award-winning XML IDE - Download a free trial today!

Don't miss another message! Subscribe to this list today.
Email
First Name
Last Name
Company
Subscribe in XML format
RSS 2.0
Atom 0.3
Site Map | Privacy Policy | Terms of Use | Trademarks
Free Stylus Studio XML Training:
W3C Member
Stylus Studio® and DataDirect XQuery ™are products from DataDirect Technologies, is a registered trademark of Progress Software Corporation, in the U.S. and other countries. © 2004-2013 All Rights Reserved.