为什么第一个apply-templates中没有select

时间:2011-06-12 20:59:37

标签: xml xslt

我正在尝试理解apply-templates,但我不明白为什么我不在apply-templates写下任何select =“nodename”:(我想到了第一个下面的应用模板我的CD收藏)

输入文档中的摘录:

<?xml version="1.0" encoding="ISO-8859-1"?>
<catalog>
    <cd>
        <title>Empire Burlesque</title>
        <artist>Bob Dylan</artist>
        <country>USA</country>
        <company>Columbia</company>
        <price>10.90</price>
        <year>1985</year>
    </cd>
    <cd>
        <title>Hide your heart</title>
        <artist>Bonnie Tyler</artist>
        <country>UK</country>
        <company>CBS Records</company>
        <price>9.90</price>
        <year>1988</year>
    </cd>
    <cd>
        <title>Greatest Hits</title>
        <artist>Dolly Parton</artist>
        <country>USA</country>
        <company>RCA</company>
        <price>9.90</price>
        <year>1982</year>
    </cd>

XSLT:

<?xml version="1.0" encoding="ISO-8859-1"?>
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">

<xsl:template match="/">
  <html>
  <body>
  <h2>My CD Collection</h2>
  <xsl:apply-templates/>
  </body>
  </html>
</xsl:template>

<xsl:template match="cd">
  <p>
  <xsl:apply-templates select="title"/>
  <xsl:apply-templates select="artist"/>
  </p>
</xsl:template>

<xsl:template match="title">
  Title: <span style="color:#ff0000">
  <xsl:value-of select="."/></span>
  <br />
</xsl:template>

<xsl:template match="artist">
  Artist: <span style="color:#00ff00">
  <xsl:value-of select="."/></span>
  <br />
</xsl:template>

</xsl:stylesheet>

取自w3schools教程。它如何理解应该选择哪个模板?

1 个答案:

答案 0 :(得分:6)

如规格:

  

如果没有select属性,xsl:apply-templates指令将处理当前节点的所有子节点,包括文本节点。

没有选择XPath的

apply-templates,在编译期间应用处理器构建的XML树视图层次结构后的模板,除非您明确驱动模板(正如您对title和{{1所做的那样) }})。

您可能还想要考虑built-in template rules的工作原理。这些规则在幕后运行,并允许在没有成功模式匹配的情况下继续递归过程。

因此,如果省略根artist的模板匹配,则无论如何都会执行模板,这要归功于内置规则。

我认为处理顺序应该是这样的:

  • 模板与根匹配,/告诉处理器将模板应用于xsl:apply-templates元素(在调用它的位置)。
  • 找不到catalog的匹配模板,因此内置规则允许继续处理其他后代元素(catalog),直到找到具有成功模式匹配的新模板({{ 1}})

内置规则在幕后运行,您必须始终将您的转换视为由模板组成,以及一些其他隐藏(但正在工作)的模板:

catalog

在您的特定情况下,上述三个模板中的前一个模板是将模板应用于cd元素的一个模板。

每次编写显式模板时都会覆盖这些内置模板。


<强>实施例

您可以通过替换:

获得相同的内容
<xsl:template match="*|/">
  <xsl:apply-templates />
</xsl:template>

<xsl:template match="text()|@*">
  <xsl:value-of select="."/>
</xsl:template>

<xsl:template match="processing-instruction()|comment()"/>

使用:

cd

关于root,在你的情况下,你也可以通过替换:

获得相同的
<xsl:template match="cd">
    <p>
        <xsl:apply-templates select="title"/>
        <xsl:apply-templates select="artist"/>
    </p>
</xsl:template>

<xsl:template match="country|company|price|year"/>

<xsl:template match="cd">
    <p>
        <xsl:apply-templates />
    </p>
</xsl:template>

或仍然:

<xsl:template match="/">
    <html>
        <body>
            <h2>My CD Collection</h2>
            <xsl:apply-templates/>
        </body>
    </html>
</xsl:template>

或仍然:

<xsl:template match="/catalog">
    <html>
        <body>
            <h2>My CD Collection</h2>
            <xsl:apply-templates/>
        </body>
    </html>
</xsl:template>