xslt计数循环_在XSLT中使用递归进行循环

xslt计数循环

XSLT已经完成 。 这意味着只要有足够的内存,XSLT就可以计算任何其他图灵完备的语言(例如C ++)可以计算的任何东西。 对于习惯于更传统语言的程序员来说,这有点令人惊讶。 毕竟,XSLT缺少一些对许多算法都很重要的功能,包括循环和可变变量。

注意: XSLT所谓的变量在大多数其他语言中称为常量 。 与传统的编程变量相比,它们更像代数变量。

功能编程

刚才提到的遗漏不是疏忽。 XSLT是一种功能语言,而不是过程性语言。 在诸如C或Pascal的过程语言中,程序被定义为一系列步骤,按指定的顺序执行将产生最终结果,作为该顺序中的最后一步。 用功能语言将程序定义为由其他功能组成的功能,对其求值可得出最终结果。 函数式语言的最大优点是执行顺序无关紧要。 作为一个简单的示例,请考虑以下两个(代数)函数:

f(x) = 2*x
g(x) = x - 3

现在考虑函数h(x)fg

h(x) = f(g(x))

你可以评估这个函数或者g第一:

h(x) = f(x - 3) = 2 * (x - 3) = 2x - 6

f首先:

h(x) = 2 * g(x) = 2 * (x - 3) = 2x - 6

两者产生相同的答案。 语言的功能性质使其更适合并行处理,因为可以同时评估程序的多个部分,而不用担心在其他部分之前需要评估哪个部分。 线程安全是自动的。

包括XSLT在内的功能语言不能包含传统循环,因为循环是按时间顺序排列的。 即,编写并编译一个典型的循环,使得i==1必须在i==2之前发生。 当然,您可以向后而不是向前运行循环,或者将循环计数器增加1以外的值,甚至可以像while语句中那样完全消除循环计数器。 但是,无论循环的类型如何,执行的顺序都很重要,这与功能编程相反。

递归

在函数式语言中,大多数由传统语言中的循环完成的任务都由递归完成。 参数代替变量。 例如,最近我被问到如何在编译时不知道要打印的数字的情况下打印一定数量的点(句点)。 例如,在格式化餐厅菜单时,这可能会很有用,在菜单名称和价格之间通常需要不同数量的点:

Crawfish Etoufee.......$9.95
Fried Chicken..........$6.95

在C中,您将编写一个简单的函数,如下所示:

void printDots(int n) {

  int i;

  for (i = 0; i < n; i++) {
    printf(".");
  }
  
}

但是,这不是解决问题的唯一方法。 可以使用递归来代替循环,如下所示:

void printDotsRecursively(int n) {

   if (n > 0) {
     printf(".");
     printDotsRecursively(n-1);
   }

}

这在C语言中是不常见的。但是,在XSLT中,递归是唯一的选择。

下面的模板生成精确传入的点数作为count参数的值。 逻辑很简单:如果$count的值大于零,则输出一个句点并以一个count参数减一的方式再次调用该函数。 否则,什么都不做。 这基本上是与printDotsRecursively函数使用的算法相同的算法,只是它是在XSLT中而不是C中实现的:

<xsl:template name="dots">
  
      <xsl:param name="count" select="1"/>

      <xsl:if test="$count > 0">
        <xsl:text>.</xsl:text>
        <xsl:call-template name="dots">
          <xsl:with-param name="count" select="$count - 1"/>
        </xsl:call-template>
      </xsl:if>
      
  </xsl:template>

例如,要打印100个点,可以使用100作为count参数的值来调用模板:

<xsl:call-template name="dots">
      <xsl:with-param name="count" select="100"/>
    </xsl:call-template>

您可以传递一些其他值来计算要打印的点数,而不必传递恒定值。 例如,以下指令在考虑了价格的长度和主菜名称(更具体地说, priceentree的字符串值的长度)后,打印了将菜单行填充到80个字符所需的点数上下文节点的子元素):

<xsl:call-template name="dots">
      <xsl:with-param name="count" 
                select="80 - string-length(entree) - string-length(price)"/>
    </xsl:call-template>

摘要

无论是在C,XSLT还是Scheme中,用递归替换循环都需要一些习惯。 但是,这种技术具有一定的优雅性。 您不需要在XSLT中经常使用它,但是它使您可以完成棘手的任务,而这些任务是在标准XSLT中无法以其他方式完成的。


翻译自: https://www.ibm.com/developerworks/xml/library/x-tiploop/index.html

xslt计数循环

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
XSLT,可以使用递归来实现循环的功能。比如,在给定数量的点的模板,可以使用递归来重复输出点的个数。下面是一个示例的XSLT模板: <xsl:template name="dots"> <xsl:param name="count" select="1"/> <xsl:if test="$count > 0"> <xsl:text>.</xsl:text> <xsl:call-template name="dots"> <xsl:with-param name="count" select="$count - 1"/> </xsl:call-template> </xsl:if> </xsl:template> 这个模板通过递归调用自身来生成指定数量的点。首先,它接收一个名为count的参数,默认值为1。然后,使用xsl:if测试count是否大于0。如果是,就输出一个点,并调用模板自身,并将count减1作为参数传递进去。这样就可以重复生成指定数量的点。 这种使用递归代替循环的技术在XSLT非常常见。尽管XSLT缺少循环和可变变量等传统编程语言常用的特性,但通过递归XSLT可以完成其他任何图灵完备语言(如C)可以完成的计算任务。这使得XSLT在处理XML数据时非常灵活和强大。<span class="em">1</span><span class="em">2</span><span class="em">3</span> #### 引用[.reference_title] - *1* *2* *3* [[转]在 XSLT 递归实现循环](https://blog.csdn.net/weixin_30621919/article/details/99142021)[target="_blank" data-report-click={"spm":"1018.2226.3001.9630","extra":{"utm_source":"vip_chatgpt_common_search_pc_result","utm_medium":"distribute.pc_search_result.none-task-cask-2~all~insert_cask~default-1-null.142^v93^chatsearchT3_2"}}] [.reference_item style="max-width: 100%"] [ .reference_list ]

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值