创建一个计数器,该计数器返回唯一子元素XSLT的增量值

时间:2014-11-20 19:00:49

标签: xml xslt

我正在尝试进行XSLT转换。我想创建一个计数器,为每个唯一的" col1"返回一个增量值。因此,例如对于具有col1" Alpha"的所有行,我想要值为1.所有具有col1" Bravo"的行。我希望值为2.而对于col1" Charlie"所有行的值都为3,其他唯一的col1将继续递增,依此类推。我是否需要创建一个变量或某种东西,将一个字符串与另一个字符串进行比较并递增它?我真的不确定如何处理这个...

 <root>
  <row>
    <col1>Alpha</col1>
    <col2>123</col2>
    <col3>ABC</col3>
  </row>
  <row>
    <col1>Alpha</col1>
    <col2>234</col2>
    <col3>BCD</col3>
  </row>
   <row>
    <col1>Bravo</col1>
    <col2>123</col2>
    <col3>ABC</col3>
  <row>
    <col1>Bravo</col1>
    <col2>234</col2>
    <col3>BCD</col3>
  </row>
  <row>
    <col1>Bravo</col1>
    <col2>345</col2>
    <col3>CDE</col3>
  </row>
  <row>
    <col1>Charlie</col1>
    <col2>123</col2>
    <col3>ABC</col3>
  </row>

2 个答案:

答案 0 :(得分:0)

如果 - 在您的previous question中 - 您的数据已经排序,则可以使用非常相似的内容:

XSLT 1.0

<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 
<xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes"/>

<xsl:template match="/root">
    <output>
        <xsl:for-each select="row">
            <xsl:copy>
                <col0>
                    <xsl:value-of select="count((. | preceding-sibling::row)[col1!=preceding-sibling::row[1]/col1])+1"/>
                </col0>
                <xsl:copy-of select="*"/>
            </xsl:copy>
        </xsl:for-each>
    </output>
</xsl:template>

</xsl:stylesheet>

这会增加col1中每个“中断”的计数,而不一定是唯一值。

答案 1 :(得分:0)

如果您可以使用XSLT 2.0,则可以使用distinct-values()index-of()的组合。

如果您的数据没有排序,它将给出第一次出现的索引。

XML输入

<root>
    <row>
        <col1>Alpha</col1>
        <col2>123</col2>
        <col3>ABC</col3>
    </row>
    <row>
        <col1>Alpha</col1>
        <col2>234</col2>
        <col3>BCD</col3>
    </row>
    <row>
        <col1>Bravo</col1>
        <col2>123</col2>
        <col3>ABC</col3>
    </row>
    <row>
        <col1>Bravo</col1>
        <col2>234</col2>
        <col3>BCD</col3>
    </row>
    <row>
        <col1>Bravo</col1>
        <col2>345</col2>
        <col3>CDE</col3>
    </row>
    <row>
        <col1>Charlie</col1>
        <col2>123</col2>
        <col3>ABC</col3>
    </row>
</root>

XSLT 2.0

<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    <xsl:output indent="yes"/>
    <xsl:strip-space elements="*"/>

    <xsl:template match="@*|node()">
        <xsl:copy>
            <xsl:apply-templates select="@*|node()"/>
        </xsl:copy>
    </xsl:template>

    <xsl:variable name="col1s" select="distinct-values(/*/row/col1)"/>

    <xsl:template match="col1">
        <col0><xsl:value-of select="index-of($col1s,.)"/></col0>
        <xsl:copy>
            <xsl:apply-templates select="@*|node()"/>
        </xsl:copy>
    </xsl:template>

</xsl:stylesheet>

<强>输出

<root>
   <row>
      <col0>1</col0>
      <col1>Alpha</col1>
      <col2>123</col2>
      <col3>ABC</col3>
   </row>
   <row>
      <col0>1</col0>
      <col1>Alpha</col1>
      <col2>234</col2>
      <col3>BCD</col3>
   </row>
   <row>
      <col0>2</col0>
      <col1>Bravo</col1>
      <col2>123</col2>
      <col3>ABC</col3>
   </row>
   <row>
      <col0>2</col0>
      <col1>Bravo</col1>
      <col2>234</col2>
      <col3>BCD</col3>
   </row>
   <row>
      <col0>2</col0>
      <col1>Bravo</col1>
      <col2>345</col2>
      <col3>CDE</col3>
   </row>
   <row>
      <col0>3</col0>
      <col1>Charlie</col1>
      <col2>123</col2>
      <col3>ABC</col3>
   </row>
</root>