如何在xslt上应用group by

时间:2013-07-25 07:53:58

标签: xslt grouping

我正在通过项目ID

尝试组合一些xml

我可以使用xslt v 2.0

我想我需要使用 for-each-group ,但我找不到类似的例子 (因为父元素)

以下是示例数据

<projects>
    <project>
        <id>141</id>
        <name>Project 141</name>
        <identifier>am-1000171</identifier>
        <description>Project 141</description>
    </project>
    <project>
        <id>120</id>
        <name>Project 120</name>
        <identifier>am-1000199</identifier>
        <description>Project 120</description>
    </project>
    <project>
        <id>109</id>
        <name>Project 109</name>
        <identifier>am-1000143</identifier>
        <description>Project 108</description>
        <parent id="141" name="Project 141" />
    </project>
    <project>
        <id>53</id>
        <name>Project 53</name>
        <identifier>am-1000101</identifier>
        <description>Project 53</description>
        <parent id="141" name="Project 141" />
    </project>
    <project>
        <id>24</id>
        <name>Project 25</name>
        <identifier>am-1000019</identifier>
        <description>Project 24</description>
        <parent id="53" name="Project 53" />
    </project>
</projects>

输出需要如下所示

120 
141
> 53
>> 24
> 109

有没有一个例子可以请任何人指点我去了解如何解决? 感谢

1 个答案:

答案 0 :(得分:1)

我不认为分组有帮助,这里的关键是交叉引用的“关键”:

<xsl:stylesheet
  xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
  version="2.0">

<xsl:param name="indent" select="'>'"/>

<xsl:output method="text"/>

<xsl:key name="children" match="project[parent]" use="parent/@id"/>

<xsl:template match="/">
  <xsl:apply-templates select="/projects/project[not(parent)]"/>
</xsl:template>

<xsl:template match="project">
  <xsl:param name="head" select="''"/>
  <xsl:value-of select="concat($head, id, '&#10;')"/>
  <xsl:apply-templates select="key('children', id)">
    <xsl:with-param name="head" select="concat($head, $indent)"/>
  </xsl:apply-templates>
</xsl:template>

</xsl:stylesheet>

这样我得到了输出

141
>109
>53
>>24
120

它只是按文档顺序处理元素,我不知道为什么你想要的输出首先有120,除非你想做一些你没有解释的排序。如果您想按id值排序,请使用

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

<xsl:param name="indent" select="'>'"/>

<xsl:output method="text"/>

<xsl:key name="children" match="project[parent]" use="parent/@id"/>

<xsl:template match="/">
  <xsl:apply-templates select="/projects/project[not(parent)]">
    <xsl:sort select="xs:integer(id)"/>
  </xsl:apply-templates>
</xsl:template>

<xsl:template match="project">
  <xsl:param name="head" select="''"/>
  <xsl:value-of select="concat($head, id, '&#10;')"/>
  <xsl:apply-templates select="key('children', id)">
    <xsl:sort select="xs:integer(id)"/>
    <xsl:with-param name="head" select="concat($head, $indent)"/>
  </xsl:apply-templates>
</xsl:template>

</xsl:stylesheet>

你得到的方式

120
141
>53
>>24
>109