首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >XSLT:使用键和条件的“value-of select”?

XSLT:使用键和条件的“value-of select”?
EN

Stack Overflow用户
提问于 2012-11-23 07:51:13
回答 1查看 7.2K关注 0票数 2

这个问题从上一个帖子开始:XSLT: Sorting based on sum of values from other nodes

现在,我可以使用键从其他节点获得我的数据总和。我似乎不能得到的是现在应用条件来选择我在使用这些键时想要的数据所需的语法或方法。

下面是我正在使用的一个简化的xml (从上一个开始修改以突出问题):

代码语言:javascript
复制
<Horses>
    <Horse>
        <ID>1</ID>
        <Name>hrsA</Name>
        <SireID>101</SireID>
        <Age>3</Age>
        <Pace>
            <Stakes>20</Stakes>
            <Wins>0</Wins>
        </Pace>
    </Horse>
    <Horse>
        <ID>2</ID>
        <Name>hrsB</Name>
        <SireID>101</SireID>
        <Age>6</Age>
        <Pace>
            <Stakes>1600</Stakes>
            <Wins>9</Wins>
        </Pace>
    </Horse>
    <Horse>
        <ID>3</ID>
        <Name>hrsC</Name>
        <SireID>101</SireID>
        <Age>3</Age>
        <Trot>
            <Stakes>200</Stakes>
            <Wins>2</Wins>
        </Trot>
    </Horse>
    <Horse>
        <ID>4</ID>
        <Name>hrsD</Name>
        <SireID>101</SireID>
        <Age>4</Age>
        <Pace>
            <Stakes>50</Stakes>
            <Wins>0</Wins>
        </Pace>
        <Trot>
            <Stakes>100</Stakes>
            <Wins>1</Wins>
        </Trot>
    </Horse>
    <Horse>
        <ID>5</ID>
        <Name>hrsE</Name>
        <SireID>101</SireID>
        <Age>3</Age>
        <Pace>
            <Stakes>100</Stakes>
            <Wins>1</Wins>
        </Pace>
        <Trot>
            <Stakes>300</Stakes>
            <Wins>1</Wins>
        </Trot>
    </Horse>
</Horses>
<Sires>
    <Sire>
        <ID>101</ID>
        <Name>srA</Name>
        <LiveFoalsALL>117</LiveFoalsALL>
    </Sire>
</Sires>

在一个场景中,我需要得到属于某个特定年龄的Sire的后代(马)。

在没有指定年龄的情况下,我使用了一个对赢下的赌注进行排序的键,如下所示(感谢Dimitre):

代码语言:javascript
复制
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
 <xsl:output omit-xml-declaration="yes" indent="yes"/>
 <xsl:key name="kOffspring" match="Horse" use="SireID"/>

 <xsl:template match="/*">
  <xsl:apply-templates select="Sires/Sire">
   <xsl:sort select="sum(key('kOffspring', ID)/*/Stakes)"
             data-type="number" order="descending"/>
  </xsl:apply-templates>
 </xsl:template>

 <xsl:template match="Sire">
    <!-- get the data I want -->
 </xsl:template>
</xsl:stylesheet>

现在,在“获取我想要的数据”中,我正在尝试仅获取3岁的马(Age=3),以仅获取3岁的获奖后代(答案= 2)我需要这样的东西,我在想:

代码语言:javascript
复制
<xsl:value-of select="count(key('kOffspring', ID)[Age=3]/*/Wins)"/>

但这并不管用。或者,我是否需要为每个年龄创建一个新的键,以便使用某些条件语法(?)像这样:

代码语言:javascript
复制
<xsl:key name="kOffspring" match="Horse[/Age=3]" use="SireID"/>

如你所见,我真的不知道我在做什么,甚至不知道这是否可能:-)

另一种类似的情况是需要计算有多少匹马获胜- answer=4 (不是获胜的数量,而是它们是以速度还是小跑的方式获胜……第三种情况需要速度或快步)。

我在Sire模板中尝试了一下:

代码语言:javascript
复制
<xsl:value-of select="count(key('kOffspring', ID)/*/Wins &gt; 0)"/>

但这只会返回1的计数。

如果这里有专家能帮助我前进,我将不胜感激。与其他编程语言相比,我发现xslt语法有点令人困惑,也很难记住-我希望我能尽快掌握它,因为它非常强大。

你好,布莱斯·斯坦伯格。

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2012-11-23 09:17:20

此转换

代码语言:javascript
复制
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
 <xsl:output omit-xml-declaration="yes" indent="yes"/>
 <xsl:key name="kOffspring" match="Horse" use="SireID"/>

 <xsl:template match="/*">
  <xsl:apply-templates select="Sires/Sire">
   <xsl:sort select="sum(key('kOffspring', ID)/*/Stakes)"
             data-type="number" order="descending"/>
  </xsl:apply-templates>
 </xsl:template>

 <xsl:template match="Sire">
     Sire <xsl:value-of select="concat(ID,' (', Name, ') Stakes: ')"/>
   <xsl:value-of select="sum(key('kOffspring', ID)/*/Stakes)"/>
     3 year old winning offspring: <xsl:value-of
     select="count(key('kOffspring', ID)[Age = 3 and */Wins > 0])"/>
     Offspring that ever were a winner: <xsl:value-of
      select="count(key('kOffspring', ID)[*/Wins > 0])"/>
 </xsl:template>
</xsl:stylesheet>

当应用于所提供的XML片段(所提供的片段,包含在单个顶层元素中以使其成为格式良好的文档)时:

代码语言:javascript
复制
<t>
    <Horses>
        <Horse>
            <ID>1</ID>
            <Name>hrsA</Name>
            <SireID>101</SireID>
            <Age>3</Age>
            <Pace>
                <Stakes>20</Stakes>
                <Wins>0</Wins>
            </Pace>
        </Horse>
        <Horse>
            <ID>2</ID>
            <Name>hrsB</Name>
            <SireID>101</SireID>
            <Age>6</Age>
            <Pace>
                <Stakes>1600</Stakes>
                <Wins>9</Wins>
            </Pace>
        </Horse>
        <Horse>
            <ID>3</ID>
            <Name>hrsC</Name>
            <SireID>101</SireID>
            <Age>3</Age>
            <Trot>
                <Stakes>200</Stakes>
                <Wins>2</Wins>
            </Trot>
        </Horse>
        <Horse>
            <ID>4</ID>
            <Name>hrsD</Name>
            <SireID>101</SireID>
            <Age>4</Age>
            <Pace>
                <Stakes>50</Stakes>
                <Wins>0</Wins>
            </Pace>
            <Trot>
                <Stakes>100</Stakes>
                <Wins>1</Wins>
            </Trot>
        </Horse>
        <Horse>
            <ID>5</ID>
            <Name>hrsE</Name>
            <SireID>101</SireID>
            <Age>3</Age>
            <Pace>
                <Stakes>100</Stakes>
                <Wins>1</Wins>
            </Pace>
            <Trot>
                <Stakes>300</Stakes>
                <Wins>1</Wins>
            </Trot>
        </Horse>
    </Horses>
    <Sires>
        <Sire>
            <ID>101</ID>
            <Name>srA</Name>
            <LiveFoalsALL>117</LiveFoalsALL>
        </Sire>
    </Sires>
</t>

会生成想要的正确结果:

代码语言:javascript
复制
 Sire 101 (srA) Stakes: 2370
 3 year old winning offspring: 2
 Offspring that ever were a winner: 4

或者,可能更有效的解决方案是使用另一个复合键,它的两个部分是SireID Age**:** 和 key

代码语言:javascript
复制
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
 <xsl:output omit-xml-declaration="yes" indent="yes"/>
 <xsl:key name="kOffspring" match="Horse" use="SireID"/>
 <xsl:key name="kOffspringBySireIdAndAge" match="Horse"
  use="concat(SireID, '+', Age)"/>

 <xsl:template match="/*">
  <xsl:apply-templates select="Sires/Sire">
   <xsl:sort select="sum(key('kOffspring', ID)/*/Stakes)"
             data-type="number" order="descending"/>
  </xsl:apply-templates>
 </xsl:template>

 <xsl:template match="Sire">
     Sire <xsl:value-of select="concat(ID,' (', Name, ') Stakes: ')"/>
   <xsl:value-of select="sum(key('kOffspring', ID)/*/Stakes)"/>
     3 year old winning offspring: <xsl:value-of
     select="count(key('kOffspringBySireIdAndAge', concat(ID, '+3'))
                       [*/Wins > 0]
                  )"/>
     Offspring that ever were a winner: <xsl:value-of
      select="count(key('kOffspring', ID)[*/Wins > 0])"/>
 </xsl:template>
</xsl:stylesheet>

当将此转换应用于相同的XML文档(如上)时,将产生相同的正确结果

代码语言:javascript
复制
 Sire 101 (srA) Stakes: 2370
 3 year old winning offspring: 2
 Offspring that ever were a winner: 4
票数 3
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/13521492

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档