2009-07-23 6 views
2

동일한 레벨 노드 이름 목록을 중복없이 표시하려고합니다.XSLT에서 같은 레벨 요소 중복 제거

의 나는 내가 C, D, E, F를 표시 할 것

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

있다고 가정 해 봅시다. 나는 출력에서 ​​중복 형제를 제거하면서 비슷한 문제에 대한 여러 가지 해결책을 찾았지만 중복 "사촌"을 제거하는 데 어려움을 겪고 있습니다.

답변

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, 요소의 선행 형제와 이름이 같은 경우 복사되지 않습니다.

+0

난 당신이'앞 - sibling'을 의미 생각합니다. ;-) 또한 같은 부모 노드에있는 노드들에 대해서만 * 같은 * 레벨의 모든 노드에서 작동하지 않습니다. *와 *는 문서에서 이미 정렬 된 경우에만 작동합니다. – Tomalak

+0

감사합니다. 축 이름을 수정했습니다. 나는 이것이 OP의 문제를 해결하지 못한다는 것을 알았다. –

+0

감사! 이것은 내 문제를 완벽하게 해결했습니다! –

1

하나의 가능성 : 귀하가 제공 한 XML에 대한

<!-- 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> 

출력 :

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