问题描述
我需要检查具有特定属性的节点是否是循环中的最后一个节点,并因此在最后一个节点之前插入和号。我尝试使用
<xsl:if test=\"position() = last()\">
似乎没有考虑到属性值。
这是XML
<creators and-others=\"no\">
<creator type=\"personal\">Roche,R.L.</creator>
<creator type=\"personal\">Moulin,D.</creator>
<creator type=\"personal\">James,K.</creator>
<creator type=\"affiliation\">CEA Centre d\'Etudes Nucleaires de Saclay,91 - Gif-sur- zYvette (France). Dept. d\'Etudes Mecaniques et Thermiques</creator>
</creators>
我需要输出as2ѭ
另外,是否有一种方法可以获取具有属性“个人”的“创建者”节点的值计数?
解决方法
为什么不计算匹配模板中的后续兄弟?同级之后的最后一个计数“ 3”节点将为零。
XSLT 2.0已在Saxon-HE 9.2.1.1J下进行了测试(在MSXSL 4.0上也被称为XSLT 1.0)
<xsl:stylesheet version=\"2.0\"
xmlns:xsl=\"http://www.w3.org/1999/XSL/Transform\"
>
<xsl:output method=\"text\"/>
<xsl:template match=\"/creators\">
<xsl:apply-templates select=\"creator\"/>
</xsl:template>
<xsl:template match=\"creator[@type=\'personal\']\">
<xsl:choose>
<xsl:when test=\"count(following-sibling::creator[@type=\'personal\'])=0\">
<xsl:text>& </xsl:text><xsl:value-of select=\".\"/>
</xsl:when>
<xsl:otherwise>
<xsl:value-of select=\".\"/><xsl:text>,</xsl:text>
</xsl:otherwise>
</xsl:choose>
</xsl:template>
<xsl:template match=\"creator\"/>
</xsl:stylesheet>
应用于您的输入,将产生:
Roche,R.L.,Moulin,D.,& James,K.
根据模板上下文,您始终可以使用axis获取节点数。例:
<xsl:template match=\"/creators\">
<xsl:variable name=\"count\" select=\"count(child::creator[@type=\'personal\'])\"/>
</xsl:template>
将$count
设置为3
。
, 您可以尝试遍历ѭ9over并在那里使用<xsl:if>
。 XPath应该选择所有那些元素,其属性type
具有值of12ѭ。
您可以在count
函数中使用类似的表达式。
, 这应该工作
<xsl:if test=\"count(//creator[@type=\'personal\']) > 0\">
Found personal
</xsl:if>
如果要将其存储在变量中
<xsl:variable name=\"PersonalCount\" select=\"count(//creator[@type=\'personal\'])\"></xsl:variable>
, 使用谓词[@type=\'personal\']
仅选择所需的<creator>
元素。这样,您的测试条件就可以工作,而无需使用任何计数或引用同级元素。您还应该测试是否只有一个<creator type=\"personal\">
,否则最终将输出一个额外的&
或逗号。因此,<xsl:choose>
比ѭ10than更方便。
下面的示例代码。如果要在现有模板中执行此操作,也可以使用ѭ9separate代替creator
单独的模板并调用<xsl:apply-templates select=\"creator[@type=\'personal\']\"/>
。
<?xml version=\"1.0\"?>
<xsl:stylesheet version=\"1.0\" xmlns:xsl=\"http://www.w3.org/1999/XSL/Transform\">
<xsl:output method=\"text\"/>
<xsl:template match=\"creators\">
<xsl:apply-templates select=\"creator[@type=\'personal\']\"/>
</xsl:template>
<xsl:template match=\"creator\">
<xsl:choose>
<xsl:when test=\"position() = 1\">
</xsl:when>
<xsl:when test=\"position() = last()\">
<xsl:text> & </xsl:text>
</xsl:when>
<xsl:otherwise>
<xsl:text>,</xsl:text>
</xsl:otherwise>
</xsl:choose>
<xsl:value-of select=\".\"/>
</xsl:template>
</xsl:stylesheet>
给定输入
<creators and-others=\"no\">
<creator type=\"personal\">Roche,R.L.</creator>
<creator type=\"personal\">Moulin,D.</creator>
<creator type=\"personal\">James,K.</creator>
<creator type=\"affiliation\">CEA Centre d\'Etudes Nucleaires de Saclay,91 - Gif-sur- zYvette (France). Dept. d\'Etudes Mecaniques et Thermiques</creator>
</creators>
它产生以下输出
Roche,D. & James,K.
, 这是一个根本不使用任何XSLT条件指令的较短解决方案:
<xsl:stylesheet version=\"1.0\"
xmlns:xsl=\"http://www.w3.org/1999/XSL/Transform\">
<xsl:output method=\"text\"/>
<xsl:strip-space elements=\"*\"/>
<xsl:template match=\"/*\">
<xsl:apply-templates select=\"creator[@type=\'personal\']\"/>
</xsl:template>
<xsl:template match=
\"creator[@type=\'personal\'][position()>1 and not(position()=last())]\">
<xsl:text>,</xsl:text>
<xsl:apply-templates/>
</xsl:template>
<xsl:template match=\"creator[@type=\'personal\'][position()=last()]\">
<xsl:text>,& </xsl:text>
<xsl:apply-templates/>
</xsl:template>
</xsl:stylesheet>
当应用于提供的XML文档时:
<creators and-others=\"no\">
<creator type=\"personal\">Roche,R.L.</creator>
<creator type=\"personal\">Moulin,D.</creator>
<creator type=\"personal\">James,K.</creator>
<creator type=\"affiliation\">CEA Centre d\'Etudes Nucleaires de Saclay,91 - Gif-sur- zYvette (France). Dept. d\'Etudes Mecaniques et Thermiques</creator>
</creators>
所需的正确结果产生了:
Roche,K.
另外,有没有一种方法来获得计数
\“ creator \”节点的值集合,其中
属性“个人”?
采用:
count(/*/creator[@type=\'personal\'])
说明:
使用模式匹配而不是XSLT条件指令。
利用XSLT(默认)处理模型和内置模板。