消除XSLT中重复的同级元素

时间:2009-07-23 13:34:56

标签: xml xslt duplicates duplicate-data

我希望显示一个相同级别的节点名称列表,没有重复项。

假设我有

<a>
    <b>
        <c />
        <d />
        <d />
    </b>
    <b>
        <e />
        <c />
        <f />
    </b>
</a>

我想要显示c,d,e,f。我找到了几个类似问题的解决方案,从输出中消除了重复的兄弟姐妹,但是我在排除重复的“表兄弟”方面遇到了麻烦。

2 个答案:

答案 0 :(得分:1)

一种可能性:

<!-- make all element nodes accessible by their nesting level -->
<xsl:key name="kNodesByLevel" match="*" use="count(ancestor-or-self::*)" />

<xsl:template match="/">
  <!-- select all nodes on one particular level -->
  <xsl:variable name="lvl" select="key('kNodesByLevel', 3)" />

  <!-- step through them... -->
  <xsl:for-each select="$lvl">
    <xsl:sort select="name()" /> 
    <xsl:variable name="name" select="name()" />
    <!-- ... and group them by node name -->
    <xsl:if test="generate-id() = generate-id($lvl[name() = $name][1])"> 
      <xsl:copy-of select="." />
    </xsl:if>
  </xsl:for-each>
</xsl:template>

您提供的XML的输出:

<c />
<d />
<e />
<f />

答案 1 :(得分:0)

我会使用XPath前兄弟轴,并检查相同的本地名称。未测试的:

<xsl:template match="c|d|e|f">
    <xsl:if test="local-name(.) != local-name(preceding-sibling::*[1])">
       <xsl:copy-of select="."/>
    </xsl:if>
</xsl:template>

IOW,如果一个元素与其前一个兄弟的名字相同,则不会被复制。