首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >如何使用XSLT在嵌套元素中维护计数?

如何使用XSLT在嵌套元素中维护计数?
EN

Stack Overflow用户
提问于 2009-11-16 11:06:00
回答 3查看 1.7K关注 0票数 1

这里问题有关。

我有表单的XML输入:

代码语言:javascript
复制
<book>
    <chapter>
        ...
    </chapter>
</book>  

我目前输出的内容如下:

代码语言:javascript
复制
<div class="book" id="book-3">
    <div class="chapter>
        ...
    </div>
</div>

使用规则<div class="book" id="book-{position()}">创建图书id。以便id的值在每个<book>节点上递增。

我想要表格的输出:

代码语言:javascript
复制
<div class="book" id="book-3">
    <div class="chapter" id="book-3-chapter-7">
        ...
    </div>
</div>

我一直试图使用一条规则,该规则从父属性中检索id属性并将其输出到子属性中。当我问这个问题时,我才意识到"../@id"永远不会匹配,因为这个属性不存在于源XML中,只有输出。

尝试将父属性作为id的一部分使用可能不是“XSLT方式”。因此,即使有一种访问输出的方法,它也可能是错误的。

一旦使用它们的id创建了章节标记,就会有我想要遵循的相同约定(因此它们有<div id="book-2-chapter12-verse212">)的分支元素。id将被单独的Java应用程序用于链接到文档,因此它必须遵循约定(即生成的id不能工作)。

使用XSLT创建这个嵌套增量计数器的最佳方法是什么?

这个问题的标题可能离我真正想问的问题相差很远,但我对XSLT的了解还不足以提出正确的问题。请随时编辑,或建议一个更好的标题。

编辑:虽然对最初的问题有很好的答案,但正如我所说,我并不确定如何正确地问这个问题。我得到了我本应该提出的问题的答案,所以我修改了这个问题。

这意味着有一些答案可以解决我的(糟糕的)原始问题,也有一个能理解我难以表达的意图的答案。我接受了后者。

我希望回答问题的其他人都能接受这一点,如果有任何建议来建议如何从一开始就回答错误的问题,我会很高兴听到的。

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2009-11-16 12:30:18

你应该看看xsl:number元素。它有许多格式化和分组结构来完成您要识别的计数和标签的类型。

这篇XML.com文章解释了如何使用一些属性为书籍、章节、节等生成多层次的数字(计数)。

类似于:

代码语言:javascript
复制
<xsl:number format="1. " level="multiple" count="book|chapter|verse"/>

在韵文模板中应用将产生:2.12.212

票数 3
EN

Stack Overflow用户

发布于 2009-11-16 11:36:32

我可能会在模板中添加一个参数,并在应用模板中使用with-param来传递它。避免所有的模棱两可。

代码语言:javascript
复制
<xsl:template match="..."> <!-- the child match -->
    <xsl:parameter name="parentId"/>
    <child id="{$parentId}-@id">
      <!-- code involving $parentId -->
    </child>
</xsl:template>

就像:

代码语言:javascript
复制
<xsl:apply-templates select="child">
    <xsl:with-param name="parentId" select="@id"/>
</xsl:apply-templates>

另一种选择是使用..等子程序--也许使用模板--在@id上进行匹配(来自两处),以避免重复。

票数 2
EN

Stack Overflow用户

发布于 2009-11-16 13:39:01

为此,我将使用一个通用函数:

代码语言:javascript
复制
<xsl:template match="*">
  <xsl:copy>
    <xsl:attribute name="id">
      <xsl:call-template name="compute-id"/>
    </xsl:attribute>
    <xsl:apply-templates />
  </xsl:copy>
</xsl:template>

<xsl:template name="compute-id">
  <xsl:param name="curr-elem" select="."/>
  <xsl:param name="id" select="''"/>
  <xsl:choose>
    <xsl:when test="$curr-elem/..">
    <xsl:call-template name="compute-id">
      <xsl:with-param name="curr-elem" select="$curr-elem/.."/>
      <xsl:with-param name="id">
        <xsl:value-of select="concat(name($curr-elem), count($curr-elem/preceding-sibling::*[name()=name($curr-elem)])+1)"/>
        <xsl:if test="$id != ''">
          <xsl:value-of select="concat('-', $id)"/>
        </xsl:if>
      </xsl:with-param>
    </xsl:call-template>
    </xsl:when>
    <xsl:otherwise>
      <xsl:value-of select="$id"/>
    </xsl:otherwise>
  </xsl:choose>
</xsl:template>
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/1741497

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档