我在谓词中使用generate-id()
函数与之前生成的id进行比较。但这不起作用,我无法弄清楚为什么。
我已经创建了一个带有输入和预期输出的示例XSLT。是的我知道 - 这段代码似乎很奇怪而且没有意义,只是要找出,为什么generate-id()
在这里不起作用。
问题行如下:
<xsl:value-of select="a[generate-id(current())=$a_id]/text()"/>
这不起作用。这里是完整的XML输入,XSLT和预期输出。
XML输入:
<root>
<test>
<a>1</a>
<a>2</a>
<a>3</a>
</test>
</root>
预期产出:
<root>
<test>
<a>1</a>
</test>
<test>
<a>2</a>
</test>
<test>
<a>3</a>
</test>
</root>
结果输出(使用id搜索找不到值):
<root>
<test>
<a/>
</test>
<test>
<a/>
</test>
<test>
<a/>
</test>
</root>
这是XSLT。问题出在最后一个模板中:
<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:output indent="yes"></xsl:output>
<xsl:template match="/root">
<xsl:copy>
<xsl:apply-templates select="test"/>
</xsl:copy>
</xsl:template>
<xsl:template match="test">
<xsl:for-each select="a">
<xsl:apply-templates select=".." mode="output">
<xsl:with-param name="a_id" select="generate-id()"/>
</xsl:apply-templates>
</xsl:for-each>
</xsl:template>
<xsl:template match="test" mode="output">
<xsl:param name="a_id"/>
<xsl:copy>
<xsl:element name="a">
<!-- Here the passed a_id cannot be found -->
<xsl:value-of select="a[generate-id(current())=$a_id]/text()"/>
</xsl:element>
</xsl:copy>
</xsl:template>
</xsl:stylesheet>
答案 0 :(得分:1)
你的问题的答案是你需要这样做......
<xsl:value-of select="a[generate-id(.)=$a_id]/text()"/>
甚至这个......
<xsl:value-of select="a[generate-id()=$a_id]/text()"/>
current()
指的是匹配的当前节点,即test
节点。 .
引用当前上下文(a
节点)。有关详细信息,请参阅Current node vs. Context node in XSLT/XPath?。
另一个答案是你可能有过于复杂的事情。你可以重新编写你的XSLT ..
<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:output indent="yes"></xsl:output>
<xsl:template match="/root">
<xsl:copy>
<xsl:apply-templates select="test"/>
</xsl:copy>
</xsl:template>
<xsl:template match="test">
<xsl:for-each select="a">
<test>
<xsl:apply-templates select="." />
</test>
</xsl:for-each>
</xsl:template>
</xsl:stylesheet>
答案 1 :(得分:1)
在template match="test"
内,current()
函数会选择匹配test
,因此我认为您只是想要
a[generate-id(.)=$a_id]
确保您将a
元素的ID与test
元素的ID与a
元素进行比较。另请注意,在XSLT 2.0中有一个is
运算符,因此您不需要传递ID并比较它们,您可以直接传递元素并输出它,或者,如果您需要比较一些基于身份的节点,使用is
运算符。