使用 XSLT 计算重复节点值

Counting duplicate node values with XSLT

我在执行一项非常基本的 XSLT 任务时遇到了问题,非常感谢任何同情我并提供帮助的人。

我需要将特定节点的每个实例的值整理成 table,并且

我的来源 XML 看起来像这样:

<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" href="graball3.xsl"?>
<collection>
 <letter id="1">
  <textString>Lorem
   <textString>ipsum</textString>
   <textString>dolor sit</textString>
   <textString>amet</textString>
   consectetur adipiscing.
  </textString>
 </letter>
 <letter id="2">
  <textString>Et amo
   <textString>ipsum</textString>
   <textString>amet</textString>
  dolor sit.
  </textString>
 </letter>
</collection>

我想输出一个 table 来给出节点的每个实例的值,包括嵌套的实例。如果两个节点的值相同,我希望有一个条目旁边有一个计数而不是两行。

所以输出会告诉我以下内容:

<table>
<tr><td>Lorem ipsum dolor sit amet consectetur adipiscing.</td><td>[1]</td></tr>
<tr><td>ispum </td><td>[2]</td></tr>
<tr><td>dolor sit </td><td>[1]</td></tr>
<tr><td>amet</td><td>[2]</td></tr>
<tr><td>Et amo ipsum dolor sit. </td><td>[1]</td></tr>
</table>

我已经尝试了解如何阅读有关 Muenchain 方法的文章。我认为这个线程可能是:

XSLT Ignore duplicate elements

但这只是为我输出节点的第一个实例(尽管计数准确。)

这是我目前的代码,是从那里复制的。

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" >
 <xsl:output method="xml" indent="yes" />
  <xsl:key name="kString" match="letter" use="//textString"/>
   <xsl:template match="@* | node()">
    <xsl:apply-templates select="@* | node()"/>
   </xsl:template>
   <xsl:template match="main">
    <table>
     <tr>
      <th>Content</th>
      <th>Count</th>
     </tr>
     <xsl:apply-templates select="collection"/>
   </table>
  </xsl:template>
   <xsl:template match="collection">
   <xsl:apply-templates select="letter[generate-id() = generate-id(key('kString', //textString)[1])]" mode="group"/>
  </xsl:template>

  <xsl:template match="letter" mode="group">
   <xsl:for-each select=".">
    <tr>
     <td>
      <xsl:value-of select="//textString"/>
     </td>
     <td>
      <xsl:value-of select="count(key('kString', //textString))"/>
     </td>
    </tr>
  </xsl:for-each>
 </xsl:template>
</xsl:stylesheet>

如有任何帮助,我将不胜感激。

这样试试:

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:strip-space elements="*"/>

<xsl:key name="kString" match="textString" use="."/>

<xsl:template match="/collection">
    <table border="1">
        <tr>
            <th>Content</th>
            <th>Count</th>
        </tr>
        <xsl:for-each select="letter//textString[generate-id()=generate-id(key('kString', .)[1])]">
            <tr>
                <td>
                    <xsl:value-of select="."/>
                </td>
                <td>
                    <xsl:value-of select="count(key('kString', .))"/>
                </td>
            </tr>
        </xsl:for-each>
   </table>
</xsl:template>

</xsl:stylesheet>