关键值和apply-template的XSLT 2.0处理问题。
<?xml version="1.0" encoding="UTF-8"?>
<ELEMENTS>
<EA-NUMERICAL ID="MyFloat_20_62045">
<NAME>MyFloat</NAME>
</EA-NUMERICAL>
<RANGEABLE-VALUE-TYPE ID="PercentType_20_62177">
<NAME>PercentType</NAME>
<BASE-RANGEABLE-REF TYPE="EA-NUMERICAL">/MyFloat_20_62045</BASE-RANGEABLE-REF>
</RANGEABLE-VALUE-TYPE>
<RANGEABLE-VALUE-TYPE ID="TorqueType_20_62239">
<NAME>TorqueType</NAME>
<BASE-RANGEABLE-REF TYPE="EA-NUMERICAL">/MyFloat_20_62045</BASE-RANGEABLE-REF>
</RANGEABLE-VALUE-TYPE>
</ELEMENTS>
XSLT报告RANGEABLE-VALUE-TYPE的关键定义:
<xsl:key name="by-rangeable-value-type" match="RANGEABLE-VALUE-TYPE" use="BASE-RANGEABLE-REF"/>
<xsl:key name="ea-numerical-type" match="EA-NUMERICAL" use="@ID"/>
然后我有两个模板(第一个用于完整信息,另一个用于之前报告EA-NUMERICAL的情况):
<!-- Reporting the full information -->
<xsl:template match="RANGEABLE-VALUE-TYPE[. is key('by-rangeable-value-type', BASE-RANGEABLE-REF)[1]]">
</xsl:template>
<!-- Reporting the reference -->
<xsl:template match="RANGEABLE-VALUE-TYPE[not(. is key('by-rangeable-value-type', BASE-RANGEABLE-REF)[1])]">
<object>
<xsl:attribute name="href">#<xsl:value-of select="tokenize(BASE-RANGEABLE-REF, '/')[last()]"/></xsl:attribute>
</object>
</xsl:template>
<xsl:apply-templates select="key('ea-numerical-type', tokenize(BASE-RANGEABLE-REF, '/')[last()])"/>
问题是EA-NUMERICAL是否在其他模板的其他地方/早些时候报告过。
现在,在第一次RANGEABLE-VALUE-TYPE处理期间,它将再次完全报告(通过使用第一个模板,如键定义状态)。对于第二个RANGEABLE-VALUE-TYPE,它正确使用参考模板。
但是XSLT 2.0中是否有一种方法可以创建/组合具有多个不同元素或属性值的键? (在此标记化BASE-RANGEABLE-REF值和EA-NUMERICAL id属性值的示例组合中?)
答案 0 :(得分:2)
您可以使用
更改密钥定义以包含两者<xsl:key name="by-rangeable-value-type"
match="RANGEABLE-VALUE-TYPE/BASE-RANGEABLE_REF | EA-NUMERICAL/@ID"
use="tokenize(., '/')[last()]"/>
现在,给定ID的密钥集将是ID属性节点和BASE-RANGEABLE-REF
元素节点的混合。要检查给定的RANGEABLE-VALUE-TYPE
是否是第一次提及,您可以使用类似
<xsl:template match="RANGEABLE-VALUE-TYPE[BASE-RANGEABLE-REF intersect
key('by-rangeable-value-type', tokenize(BASE-RANGEABLE-REF, '/')[last()])[1]]">
如果这是第一个匹配的BASE-RANGEABLE-REF
并且之前没有EA-NUMERICAL
,它将匹配。
然后,您还需要两种模式来报告完整信息&#34;模板,因此您可以将EA-NUMERICAL
映射到交叉引用(如果已经完整报告了RANGEABLE-VALUE-TYPE
<xsl:template match="EA-NUMERICAL" mode="copy" name="copy-ean">
<!-- whatever you do to report the full details -->
</xsl:template>
<!-- first mention (i.e. not yet mentioned in any RANGEABLE-VALUE-TYPE) -->
<xsl:template match="EA-NUMERICAL[@ID is key('by-rangeable-value-type', @ID)[1]]">
<xsl:call-template name="copy-ean" />
</xsl:template>
<!-- other mentions becom href -->
<xsl:template match="EA-NUMERICAL">
<object href="#{@ID}" />
</xsl:template>
并在您的&#34;首先RANGEABLE-VALUE-TYPE
&#34;模板使用
<xsl:apply-templates mode="copy" select="key('ea-numerical-type', tokenize(BASE-RANGEABLE-REF, '/')[last()])"/>