我需要根据输入xml的内容标签输出不同的节点。
正如您将在转换中看到的那样,我想认识到,如果关闭的SHU_CODE = 10、6、7、8、9,它应该进入一个NODE节点,但是如果它的SHU_CODE = 4,它应该进入一个节点。进入一个单独的节点。
然后在每个节点中,我将转换应用于每个特定的关闭。
我遇到的问题是我无法设法拥有单独的节点,所有节点都转到相同的节点。
这是输入xml:
<Inserts>
<Shuts>
<Shut>
<SHU_CODE>10</SHU_CODE>
</Shut>
<Shut>
<SHU_CODE>4</SHU_CODE>
</Shut>
</Shuts>
</Inserts>
这是我的预期输出:
<NODE>
<SHUT workcenter='10'/>
</NODE>
<NODE>
<SHUT workcenter='4'/>
</NODE>
这是我的xsl转换的一部分:
<xsl:template match="Inserts/Shuts[Shut/SHU_CODE='10']
| Inserts/Shuts[Shut/SHU_CODE='6']
| Inserts/Shuts[Shut/SHU_CODE='7']
| Inserts/Shuts[Shut/SHU_CODE='8']
| Inserts/Shuts[Shut/SHU_CODE='9']">
<xsl:text>
</xsl:text>
<xsl:text disable-output-escaping="yes"><</xsl:text>NODE<xsl:text
disable-output-escaping="yes">></xsl:text>
<xsl:text>
</xsl:text>
<xsl:apply-templates select="Shut[SHU_CODE='10']
| Shut[SHU_CODE='6']
| Shut[SHU_CODE='7']
| Shut[SHU_CODE='8']
| Shut[SHU_CODE='9']"/>
<xsl:text disable-output-escaping="yes"></</xsl:text>NODE<xsl:text disable-output-escaping="yes">></xsl:text>
</xsl:template>
<xsl:template match="Inserts/Shuts[Shut/SHU_CODE='4']">
<xsl:text>
</xsl:text>
<xsl:text disable-output-escaping="yes"><</xsl:text>NODE<xsl:text disable-output-escaping="yes">></xsl:text>
<xsl:text>
</xsl:text>
<xsl:apply-templates select="Shut[SHU_CODE='4']"/>
<xsl:text disable-output-escaping="yes"></</xsl:text>NODE<xsl:text disable-output-escaping="yes">></xsl:text>
</xsl:template>
答案 0 :(得分:0)
假设您可以移至XSLT 2或3,则可以使用xsl:for-each-group
轻松完成此操作:
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
version="3.0">
<xsl:output indent="yes"/>
<xsl:mode on-no-match="shallow-copy"/>
<xsl:template match="Shuts">
<xsl:for-each-group select="Shut" group-by="SHU_CODE = 4">
<NODE>
<xsl:apply-templates select="current-group()"/>
</NODE>
</xsl:for-each-group>
</xsl:template>
<xsl:template match="Shut">
<SHUT workcenter="{SHU_CODE}"/>
</xsl:template>
</xsl:stylesheet>
https://xsltfiddle.liberty-development.net/eiZQaFB有一个在线示例。在XSLT 1中,通常使用Muenchian分组和一个密钥进行分组。
如果要基于不同的值形成不同的组,则需要某种方式来定义这些组,假设具有XPath 3.1的XSLT 3可以使用一系列数组,然后在其中检查索引。 https://xsltfiddle.liberty-development.net/eiZQaFB/1
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:array="http://www.w3.org/2005/xpath-functions/array"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
xmlns:mf="http://example.com/mf"
exclude-result-prefixes="xs array mf"
version="3.0">
<xsl:param name="group-keys" as="array(xs:integer)*" select="[4], [11], array{6 to 10}"/>
<xsl:function name="mf:group-index" as="xs:integer">
<xsl:param name="seq-of-arrays" as="array(xs:integer)*"/>
<xsl:param name="code" as="xs:integer"/>
<xsl:sequence select="for $pos in 1 to count($seq-of-arrays)
return $pos[array:flatten($seq-of-arrays[$pos]) = $code]"/>
</xsl:function>
<xsl:output indent="yes"/>
<xsl:mode on-no-match="shallow-copy"/>
<xsl:template match="Shuts">
<xsl:for-each-group select="Shut" group-by="mf:group-index($group-keys, SHU_CODE)">
<NODE>
<xsl:apply-templates select="current-group()"/>
</NODE>
</xsl:for-each-group>
</xsl:template>
<xsl:template match="Shut">
<SHUT workcenter="{SHU_CODE}"/>
</xsl:template>
</xsl:stylesheet>