请看以下两个例子:
<foo>some text <bar/> and maybe some more</foo>
和
<foo>some text <bar/> and a last <bar/></foo>
bar
元素中的混合文本节点和foo
元素。现在我在foo
,想知道最后一个孩子是bar
。第一个例子应该被证明是错误的,因为bar
之后有文本,但第二个例子应该是真的。
如何使用XSLT实现此目的?
答案 0 :(得分:13)
只需选择<foo>
元素的最后一个节点,然后使用self
轴来解析节点类型。
/foo/node()[position()=last()]/self::bar
如果最后一个节点不是元素,则此XPath表达式返回一个空集(等同于布尔值false)。如果要专门获取值true
或false
,请将此表达式包装在XPath函数boolean()
中。使用self::*
代替self::bar
来匹配任何元素作为最后一个节点。
输入XML文档:
<root>
<foo>some text <bar/> and maybe some more</foo>
<foo>some text <bar/> and a last <bar/></foo>
</root>
XSLT文档示例:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="text"/>
<xsl:template match="foo">
<xsl:choose>
<xsl:when test="node()[position()=last()]/self::bar">
<xsl:text>bar element at the end </xsl:text>
</xsl:when>
<xsl:otherwise>
<xsl:text>text at the end </xsl:text>
</xsl:otherwise>
</xsl:choose>
</xsl:template>
</xsl:stylesheet>
样式表的输出:
text at the end
bar element at the end
答案 1 :(得分:7)
现在我在
foo
,想找到 如果最后一个孩子是bar
使用强>:
node()[last()][self::bar]
任何非空节点集的布尔值为true()
,否则为false()
。您可以直接使用上述表达式(未修改)作为任何test
或<xsl:if>
的{{1}}属性的值。
更好,使用:
<xsl:when>
作为foo/node()[last()][self::bar]
的{{1}}属性 - 因此您以纯粹的“推送”风格书写。
答案 2 :(得分:5)
更新: 此答案解决了原始问题标题中所述的要求,“查明最后一个子节点是否为文本节点”。但问题机构提出了不同的要求,而后者的要求似乎是OP所要求的。
前两个答案明确地测试最后一个孩子是否是bar
元素,而不是直接测试它是否是文本节点。如果foo仅包含 “混合文本节点和条形元素”且永远不会有零个孩子,这是正确的。
但您可能想直接测试最后一个孩子是否是文本节点:
也许你知道后两种情况永远不会发生在你的情况下(但是从你的问题我猜想#3可以)。或者也许你是这么想但不确定,或者你没有想过它。无论哪种情况,直接测试你真正想知道的东西都更安全:
test="node()[last()]/self::text()"
因此,在@Dimitre的示例代码和输入的基础上,使用以下XML输入:
<root>
<foo>some text <bar/> and maybe some more</foo>
<foo>some text <bar/> and a pi: <?foopi param=yes?></foo>
<foo>some text <bar/> and a comment: <!-- baz --></foo>
<foo>some text and an element: <bar /></foo>
<foo noChildren="true" />
</root>
使用此XSLT模板:
<xsl:template match="foo">
<xsl:choose>
<xsl:when test="node()[last()]/self::text()">
<xsl:text>text at the end; </xsl:text>
</xsl:when>
<xsl:when test="node()[last()]/self::*">
<xsl:text>element at the end; </xsl:text>
</xsl:when>
<xsl:otherwise>
<xsl:text>neither text nor element child at the end; </xsl:text>
</xsl:otherwise>
</xsl:choose>
</xsl:template>
的产率:
text at the end;
neither text nor element child at the end;
neither text nor element child at the end;
element at the end;
neither text nor element child at the end;