使用当前节点的位置来访问另一个节点的值

时间:2013-04-24 10:21:18

标签: xpath xslt-2.0

我有一个近似于表格布局的xml源代码(程序输出) - a是表格持有者,b是列标题d,c是行,e是行单元格:

<?xml version="1.0" encoding="utf-16"?>
    <a>
    <b>
        <d/>
        <d/>
        <d/>
    </b>
        <c>
        <e/>
            <e/>
        <e/>
        </c>
    </a>
</xml>

我写了以下xsl:

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

<xsl:template match="/">
    <Lessons>
    <xsl:for-each select="//c">
        <xsl:call-template name="lesson" />
    </xsl:for-each>
    </Lessons>
</xsl:template>


<xsl:template name="lesson">
    <Lesson>
        <Teacher>
            <xsl:value-of select="count(./preceding-sibling::*)+1" />
            <xsl:value-of select="//b[count(./preceding-sibling::*)+1]" />
        </Teacher>
    </Lesson>
</xsl:template>

</xsl:stylesheet>

Teacher元素的第一个xsl:value-of为我提供了正确的值。我希望第二个xsl:value-of返回该单元格标题的值,即对于调用模板的第一个e元素,返回第一个d元素,依此类推。但是,它输出所有d元素的值。

1 个答案:

答案 0 :(得分:0)

即使不完全清楚你的期望,我也会尝试回答 据我所知,您希望找到与<d>元素具有相同位置的<e>元素。

将当前位置作为变量获取是可能的。

xsl:variable name ="pos" select="position()" />
<xsl:value-of select="//b/d[position() = $pos]/@id" />

或使用preceding-sibling

的计数
<xsl:value-of select="//b/d[(count(current()/preceding-sibling::*)+1)]/@id" />

更新由于“所有行业的乔治”中的评论,以下部分已更改。

请注意position()的结果取决于调用上下文。

例如,在测试xslt(版本1.0)之后:

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

    <xsl:template match="/">
        <Lessons>
            <!-- Wrong result with position  -->
            <xsl:for-each select="//c/e">
                <xsl:call-template name="lesson" />
            </xsl:for-each>
        </Lessons>
        <Lessons2>
            <!-- Wonted result even with position -->
            <xsl:for-each select="//c">
                <xsl:for-each select="e">
                    <xsl:call-template name="lesson" />
                </xsl:for-each>
            </xsl:for-each>
        </Lessons2>
    </xsl:template>

    <xsl:template name="lesson">
        <Lesson>
            <Teacher>
                <xsl:value-of select="@id" />
                <xsl:text>,</xsl:text>
                <xsl:value-of select="count(./preceding-sibling::*)+1" />
                <xsl:text>,</xsl:text>
                <xsl:variable name ="pos" select="position()" />
                <xsl:value-of select="$pos" />
                <xsl:text>,</xsl:text>
                <xsl:value-of select="//b/d[position() = $pos]/@id" />
                <xsl:text>,</xsl:text>
                <xsl:value-of select="//b/d[count(current()/preceding-sibling::*)+1]/@id" />
            </Teacher>
        </Lesson>
    </xsl:template>

</xsl:stylesheet>

使用此输入:

<?xml version="1.0" encoding="utf-16"?>
<xml>
    <a>
        <b>
            <d id="d1"/>
            <d id="d2"/>
            <d id="d3"/>
        </b>
        <c>
            <e id="e1"/>
            <e id="e2"/>
            <e id="e3"/>
        </c>
        <c>
            <e id="e21"/>
            <e id="e22"/>
            <e id="e23"/>
        </c>
        <c>
            <e id="e21"/>
            <e id="e22"/>
            <e id="e23"/>
        </c>
    </a>
</xml>

生成此输出:

<Lessons>
  <Lesson>
    <Teacher>e1,1,1,d1,d1</Teacher>
  </Lesson>
  <Lesson>
    <Teacher>e2,2,2,d2,d2</Teacher>
  </Lesson>
  <Lesson>
    <Teacher>e3,3,3,d3,d3</Teacher>
  </Lesson>
  <Lesson>
    <Teacher>e21,1,4,,d1</Teacher>
  </Lesson>
  <Lesson>
    <Teacher>e22,2,5,,d2</Teacher>
  </Lesson>
  <Lesson>
    <Teacher>e23,3,6,,d3</Teacher>
  </Lesson>
  <Lesson>
    <Teacher>e21,1,7,,d1</Teacher>
  </Lesson>
  <Lesson>
    <Teacher>e22,2,8,,d2</Teacher>
  </Lesson>
  <Lesson>
    <Teacher>e23,3,9,,d3</Teacher>
  </Lesson>
</Lessons><Lessons2>
  <Lesson>
    <Teacher>e1,1,1,d1,d1</Teacher>
  </Lesson>
  <Lesson>
    <Teacher>e2,2,2,d2,d2</Teacher>
  </Lesson>
  <Lesson>
    <Teacher>e3,3,3,d3,d3</Teacher>
  </Lesson>
  <Lesson>
    <Teacher>e21,1,1,d1,d1</Teacher>
  </Lesson>
  <Lesson>
    <Teacher>e22,2,2,d2,d2</Teacher>
  </Lesson>
  <Lesson>
    <Teacher>e23,3,3,d3,d3</Teacher>
  </Lesson>
  <Lesson>
    <Teacher>e21,1,1,d1,d1</Teacher>
  </Lesson>
  <Lesson>
    <Teacher>e22,2,2,d2,d2</Teacher>
  </Lesson>
  <Lesson>
    <Teacher>e23,3,3,d3,d3</Teacher>
  </Lesson>
</Lessons2>