如何使用XSL变量作为评估XPath的条件?

时间:2013-01-17 11:25:30

标签: xslt xpath

使用变量作为XPath评估的条件时,我遇到了一个问题。我有以下模板可以正常工作:

<xsl:template name="typeReasonDic">
    <xsl:variable name="dic" select="$schema//xs:simpleType[@name = 'type_reason_et']"/>
    <!-- do something with the variable -->
</xsl:template>

但是,当我将其更改为如下所示:

<xsl:template name="typeReasonDic">
    <xsl:param name="choose_dic" select="@name = 'type_reason_et'"/>

    <xsl:variable name="dic" select="$schema//xs:simpleType[$choose_dic]"/>
    <!-- do something with the variable -->
</xsl:template>

无法找到所需的节点。

我希望获得的是$choose_dic默认值的模板,可以在必要时覆盖。

我在这里缺少什么?

UPD:我找到的this链接描述了我正在尝试做的事情,但它似乎对我不起作用。

3 个答案:

答案 0 :(得分:1)

通过

<xsl:param name="choose_dic" select="@name = 'type_reason_et'"/>

XSL引擎将尝试将“@name ='type_reason_et'”评估为XPath表达式,并将RESULT分配给您的变量。

您应该使用以下变量声明:

<xsl:param name="choose_dic">@name = 'type_reason_et'</xsl:param>

这是默认值,但您可以在使用xsl:with-param调用模板时覆盖它。

答案 1 :(得分:1)

XSLT不是一种宏语言,您可以在运行时将代码与字符串连接起来,然后动态评估它们。因此,总的来说,您需要一个扩展函数来评估存储在字符串中的XPath表达式,或者您需要查看新的XSLT 3.0功能,如http://www.saxonica.com/documentation/xsl-elements/evaluate.xml

XSLT 1.0或2.0的范围可能是这样做的。

<xsl:param name="p1" select="'foo'"/>

<xsl:variable name="v1" select="//bar[@att = $p1]"/>

其中param包含您与其他值比较的值,例如属性或元素节点等节点中的值。

答案 2 :(得分:1)

如果没有扩展功能,则无法在XSLT 1.0或2.0中直接执行此操作。问题在于

<xsl:template name="typeReasonDic">
    <xsl:param name="choose_dic" select="@name = 'type_reason_et'"/>

    <xsl:variable name="dic" select="$schema//xs:simpleType[$choose_dic]"/>
    <!-- do something with the variable -->
</xsl:template>

<xsl:param>将在当前上下文中一次评估其select表达式,并将此评估的真/假结果存储在$choose_dic变量中。因此,<xsl:variable>会在xs:simpleType下选择所有 $schema元素(如果$choose_dic为真)或他们(如果$choose_dic)是假的。这与

非常不同
<xsl:variable name="dic" select="$schema//xs:simpleType[@name = 'type_reason_et']"/>

将在每个@name = 'type_reason_et'的上下文中重复评估xsl:simpleType,并选择表达式评估为true的元素。

如果您将XPath表达式存储为字符串,则可以使用扩展函数,例如dyn:evaluate或XSLT 3.0 xsl:evaluate元素,如果您使用的是Saxon。