XSLT中具有相同名称的多个子节点

时间:2014-01-18 11:14:48

标签: xml xslt xpath

我有以下XML:

<catalog>
    <cd>
        <title>Empire Burlesque</title>
        <artist>Artist 1</artist>
        <country>USA</country>
        <artist>Artist 2</artist>
        <artist>Artist 3</artist>
        <company>Columbia</company>
        <price>10.90</price>
        <year>1985</year>
    </cd>
</catalog>

现在在XSLT中我想循环遍历<cd>的子节点并检查它是<title>还是<artist>还是<country>等...到目前为止我做了以下XSLT:

<xsl:for-each select="catalog/cd">
        <table>
            <tr>
                <th colspan="2"><xsl:value-of select="title"/></th>
            </tr>
            <xsl:choose>
                <xsl:when test="artist">
                    <xsl:apply-templates select="artist"/>
                </xsl:when>
                <xsl:when test="country">
                    <xsl:apply-templates select="country"/>
                </xsl:when>
                <xsl:when test="company">
                    <xsl:apply-templates select="company"/>
                </xsl:when>
                <xsl:when test="price">
                    <xsl:apply-templates select="price"/>
                </xsl:when>
                <xsl:otherwise>
                    <xsl:apply-templates select="year"/>
                </xsl:otherwise>
            </xsl:choose>
</xsl:for-each>

但由于某种原因<artist>显示第一个,只有其他人没有显示。我想要的是即使有<artist><country>和另一个<artist>,依次显示每个节点。有没有人有任何想法?

1 个答案:

答案 0 :(得分:1)

您只需完全删除choose即可。一旦xsl:choose遇到第一次成功的when测试,artist就会停止,基本上你会说“如果有country然后显示,否则如果有<xsl:for-each select="catalog/cd"> <table> <tr> <th colspan="2"><xsl:value-of select="title"/></th> </tr> <xsl:apply-templates select="artist"/> <xsl:apply-templates select="country"/> <xsl:apply-templates select="company"/> <xsl:apply-templates select="price"/> <xsl:apply-templates select="year"/> </table> </xsl:for-each> 那么表明,否则......“。

apply-templates

在应用模板之前,您无需检查元素是否存在; select将处理其select表达式找到的所有节点,如果apply-templates找不到任何内容,则apply-templates将不执行任何操作。

如果您想按文档顺序处理元素而不是首先处理艺术家,那么国家/地区等等只需将它们分组为一个<xsl:apply-templates select="artist | country | company | price | year" />

title

或者如果您不想明确地命名所有元素,那么将<xsl:template match="title"> <tr> <th colspan="2"><xsl:value-of select="."/></th> </tr> </xsl:template> 逻辑移动到自己的模板中

<xsl:for-each select="catalog/cd">
    <table>
        <xsl:apply-templates select="*" />
    </table>
</xsl:for-each>

然后你的主模板可以简单地

{{1}}