1

我有一个包含多个帐户的 XML,我正在尝试使用 score/max_score 格式对多个分数求和。

XML:

<?xml version="1.0" encoding="UTF-8"?>
<?xml-stylesheet type="text/xsl" href="accounts.xsl"?>

<accounts>
    <account active="yes">
        <id>1</id>
        <name>James</name>
        <score>50/100</score>
    </account>
    <account active="yes">
        <id>2</id>
        <name>Caty</name>
        <score>10/100</score>
    </account>
    <account active="yes">
        <id>3</id>
        <name>Acacia</name>
        <score>30/100</score>
    </account>
    <account active="yes">
        <id>4</id>
        <name>James</name>
        <score>50/100</score>
    </account>
    <account active="yes">
        <id>5</id>
        <name>Scoot_5</name>
        <score>40/100</score>
    </account>
</accounts>

和 XSLT:

<?xml version="1.0"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="2.0">

    <xsl:template match="/">
        <html>
            <body>

                <p>
                    <xsl:value-of select="sum(//accounts/account/score/number(substring-before(.,'/')))"/>  
                </p>

            </body>
        </html>
    </xsl:template>
</xsl:stylesheet>

但是,当我运行 xml 时说它有错误并且不返回总和。为什么?

4

2 回答 2

2

问题是您的XSLT 2.0 转换无法在 Web 浏览器中工作,后者仅在本机支持 XSLT 1.0

有关在 XSLT 1.0 中对元素求和的方法,请参阅 Michael Kay 对 XSLT 1 的回答和 sum 函数以获得一般想法。有关某些代码示例,请参阅 Dimitre Novatchev 对乘以 2 个数字然后用 XSLT 求和的答案。有关 Web 浏览器中对 XSLT 2.0 的实际支持,请参阅Saxon-CE

我喜欢递归方法。以下是它如何适用于您的问题:

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

  <xsl:template match="/">
    <html>
      <body>
        <p>
          <xsl:call-template name="sumScores">
            <xsl:with-param name="pList" select="/accounts/account/score"/>
          </xsl:call-template>
        </p>
      </body>
    </html>
  </xsl:template>

  <xsl:template name="sumScores">
    <xsl:param name="pList"/>
    <xsl:param name="pAccum" select="0"/>
    <xsl:choose>
      <xsl:when test="$pList">
        <xsl:variable name="vHead" select="$pList[1]"/>
        <xsl:call-template name="sumScores">
          <xsl:with-param name="pList" select="$pList[position() > 1]"/>
          <xsl:with-param name="pAccum"
                          select="$pAccum + number(substring-before($vHead,'/'))"/>
        </xsl:call-template>
      </xsl:when>
      <xsl:otherwise>
        <xsl:value-of select="$pAccum"/>
      </xsl:otherwise>
    </xsl:choose>
  </xsl:template>

</xsl:stylesheet>

(来源:源自Dimitre Novatchev 编写的类似代码。)

当这个 XSLT 1.0 转换与您的输入 XML 一起运行时,我们会得到所需的 HTML 输出:

<html>
   <body>
      <p>180</p>
   </body>
</html>
于 2013-10-28T22:42:42.987 回答
1

It seems that @kjhughes somehow worked out that you were using an XSLT 1.0 processor and that you were running in a web browser.

You need an XSLT 2.0 processor to run this. If you are indeed running in a web browser, consider Saxon-CE, which is currently the only 2.0 processor to run client-side.

于 2013-10-29T09:04:12.227 回答