用于计算具有相同标记名称的子节点的xpath

时间:2013-10-20 04:55:34

标签: xml xslt xpath count

我需要找到所有的书,如果这本书有多个作者,请写下第一个作者的名字和“et al”之后的名字。下面是我的代码和第一本书用“JK Rowling等”打印但是它没有为第二本书工作。

这是xml代码

 <bookstore>
 <book>
 <title category="fiction">Harry Potter</title>
 <author>J. K. Rowling</author>
<author>sxdgfds</author>
<publisher>Bloomsbury</publisher>
 <year>2005</year>
 <price>29.99</price>
 </book>
 <book>
 <title category="fiction">The Vampire Diaries</title>
 <author>L.J. Smith</author>
 <author>sdgsdgsdgdsg</author>
<publisher>Bloomsbury</publisher>
 <year>2004</year>
 <price>25.99</price>
 </book>
 <book>
 <title category="fiction">The DaVinci Code</title>
 <author>Dan Brown</author>
<publisher>Bloomsbury</publisher>
 <year>2002</year>
 <price>35.99</price>
 </book>

这是xslt代码

 <xsl:for-each select="//book[30 >price]">

    <xsl:if test="title[@category='fiction']">

             <span style="color:blue;font-weight:bold"><xsl:value-of select="title"/></span><br />
             <xsl:choose>
                <xsl:when test="count(./author)>1">
                    <span style="color:red;font-style:italic"><xsl:value-of select="author"/></span>
                    <span style="color:red;font-style:italic"> et al</span><br />
                </xsl:when>
                <xsl:otherwise>
                    <span style="color:red;font-style:italic"><xsl:value-of select="author"/></span><br />
                </xsl:otherwise>
            </xsl:choose>
             <span><xsl:value-of select="price"/></span><br />

    </xsl:if>

  </xsl:for-each>

我试图计算有多少作者在那里,但似乎我对计数函数的路径有问题。任何帮助都将不胜感激。

1 个答案:

答案 0 :(得分:1)

您的代码似乎没问题,但同样的事情可以表达得更简单。

<xsl:for-each select="//book[price &lt; 30]">
    <xsl:if test="title[@category='fiction']">
        <span style="color:blue;font-weight:bold"><xsl:value-of select="title"/></span><br />
        <span style="color:red;font-style:italic"><xsl:value-of select="author[1]" /></span>
        <xsl:if test="author[2]">
            <span style="color:red;font-style:italic"> et al</span>
        </xsl:if>
        <br />
        <span><xsl:value-of select="price"/></span><br />
    </xsl:if>
</xsl:for-each>

上面比你的代码短,但它不是很优雅。这样更好。

<xsl:template match="/">
  <xsl:apply-templates select="//book[price &lt; 30 and @category='fiction']" />
</xsl:template>

<xsl:template match="book">
  <div class="book">
    <div class="title"><xsl:value-of select="title"/></div>
    <div class="author">
      <xsl:value-of select="author[1]" /><xsl:if test="author[2]"> et al</xsl:if>
    </div>
    <div class="price"><xsl:value-of select="price"/></div>
  </div>
</xsl:template>
  • 编写可以显示每本书的通用模板,例如此书。
  • 通过<xsl:apply-templates>使用它们,而不是重复使用<xsl:for-each>
  • 使用CSS设置输出样式。内联样式很难看。