2010-10-23 115 views
2

我试图用我在网上看到的递归习惯用法来创建类似于for-loop的东西。我的实现是用一个参数来告诉打印什么。我使用Eclipse的内置XSL transformator,我不能为我的生活为什么它给出了一个StackOverflowException:XSL - 为什么这个递归永远?

<!-- 
    Loops recursively to print something the number of times specified with 
    the max parameter. 
    The print parameter tells what to print. 
--> 
<xsl:template name="loop"> 
    <xsl:param name="count" select="1"/> 
    <xsl:param name="max" /> 
    <xsl:param name="print" /> 
    <xsl:if test="not($count = $max)"> 

     <xsl:value-of select="$print" /> 

     <xsl:call-template name="loop"> 
      <xsl:with-param name="count"> 
       <xsl:value-of select="$count + 1" /> 
      </xsl:with-param> 
      <xsl:with-param name="max"> 
       <xsl:value-of select="$max"/> 
      </xsl:with-param> 
      <xsl:with-param name="print"> 
       <xsl:value-of select="$print" /> 
      </xsl:with-param> 
     </xsl:call-template> 
    </xsl:if> 
</xsl:template> 

而且,为什么$count < $max放弃无效的XPath表达式?

在此先感谢。

+0

问得好,+1。请参阅我的回答以获得详细的解释并回答您的两个问题。 :) – 2010-10-23 16:29:55

回答

3

我不能为我的生活为什么它 给出了一个StackOverflowException

为 “停止” 的代码是太弱的检查

<xsl:if test="not($count = $max)">  

这将永远是true()如果$max小于$count,如果其中一个或两个$max$count不具有整数值,或者它们未定义。

而且,为什么$数< $最大给 无效的XPath表达式?

您可以使用

not($count >= $max) 

,从而避免需要躲避<字符。

最后,另外一个问题,没有直接关系的主要问题:

从未在<xsl:with-param><xsl:param><xsl:variable>身体指定参数(原子)值。这会创建一个RTF(结果树片段),并且每次引用参数/变量时都需要转换为适当的原子值。这是效率低下,难以阅读和维护,并可能导致错误。

而不是

 <xsl:with-param name="count">    
      <xsl:value-of select="$count + 1" />    
     </xsl:with-param>    

 <xsl:with-param name="count" select="$count + 1" />    
+0

感谢您的详细解释。 – 2010-10-23 19:07:29

3

此外,为什么$ count < $ max给 无效的Xpath表达式?

您应该使用&lt;而不是<符号。

+0

谢谢。它起作用,如果我使用这个条件,并从0开始,所以我假设无限递归与我以前的条件有关。 – 2010-10-23 11:00:25