2012-02-07 105 views
2

我嘗試瞭解XSLT 2.0中的分組函數。我的源文件是XSLT:將扁平列表變成層次結構

<root> 
    <entry level="a" name="aaa"/> 
    <entry level="a" name="bbb"/> 
    <entry level="b" name="ccc"/> 
    <entry level="c" name="ddd"/> 
    <entry level="a" name="eee"/> 
    <entry level="a" name="fff"/> 
    <entry level="b" name="ggg"/> 
</root> 

,結果應該是這樣的

<section name="aaa"/> 
<section name="bbb"> 
    <section name="ccc"> 
    <section name="ddd" /> 
    </section> 
</section> 
<section name="eee"/> 
<section name="fff"> 
    <section name="ggg" /> 
</section> 

那就是:如果有一個更深層次的一個下面的項(b比一個更深刻,...)的下一節應該是當前的子節點,如果是同一級別,則應該是下一個兄弟節點。

我試過xsl:group-by select="entry" group-by="@level"這給了我一個合理的分組,但我不知道如何打開該部分下來,如果有一個下跌。

another similar question其中規定:「在XSLT 2.0中,使用新的分組函數會相當容易。」 - 這可能很容易,但我不明白。

+0

以上運行時,你有或將有可能被無限水平的水平固定數目的? – Chris 2012-02-07 12:46:45

+0

@Chris有一個固定的層數(4)。 – topskip 2012-02-07 12:54:05

回答

3

下面是一個例子:

<xsl:stylesheet 
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
    xmlns:xs="http://www.w3.org/2001/XMLSchema" 
    xmlns:mf="http://example.com/mf" 
    exclude-result-prefixes="xs mf" 
    version="2.0"> 

    <xsl:output indent="yes"/> 

    <xsl:function name="mf:group" as="element(section)*"> 
    <xsl:param name="entries" as="element(entry)*"/> 
    <xsl:param name="level" as="xs:string"/> 
    <xsl:for-each-group select="$entries" group-starting-with="entry[@level = $level]"> 
     <section name="{@name}"> 
     <xsl:sequence select="mf:group(current-group() except ., codepoints-to-string(string-to-codepoints($level)[1] + 1))"/> 
     </section> 
    </xsl:for-each-group> 
    </xsl:function> 

    <xsl:template match="root"> 
    <xsl:copy> 
     <xsl:sequence select="mf:group(entry, 'a')"/> 
    </xsl:copy> 
    </xsl:template> 

</xsl:stylesheet> 

應該從 'A' 到 'Z' 的任何層面開展工作。

撒克遜9.4,對

<root> 
    <entry level="a" name="aaa"/> 
    <entry level="a" name="bbb"/> 
    <entry level="b" name="ccc"/> 
    <entry level="c" name="ddd"/> 
    <entry level="a" name="eee"/> 
    <entry level="a" name="fff"/> 
    <entry level="b" name="ggg"/> 
</root> 

輸出

<root> 
    <section name="aaa"/> 
    <section name="bbb"> 
     <section name="ccc"> 
     <section name="ddd"/> 
     </section> 
    </section> 
    <section name="eee"/> 
    <section name="fff"> 
     <section name="ggg"/> 
    </section> 
</root> 
+0

對不起,我只能一勞永逸。真棒。 – topskip 2012-02-07 14:03:56