获取包含来自另一个节点集XSLT1.0的值的节点集

时间:2016-02-08 23:24:38

标签: xslt-1.0

我正在使用XSLT1.0,无法使用任何扩展程序。我有一个节点集,需要找到另一个节点集中包含第一个值的所有元素,并将它们列为相关节点。

以下示例有点人为,因为我正在使用的XML非常大并且包含机密数据,因此我编写了一些数据。

在以下XML的示例中,我正在处理集合。当我到set_no 1时,我发现有子集1,2& 3.然后我需要找到并以sub_sec顺序列出,所有book / chapter / section / sub_section / sub_sec元素,其sec_no在1,2,3(sets / set1 / sub_set值)

所以我的结果应该是:

set1 
A
B
C
D
E
F
G

set2
A
B
C
D
G 

在SQL中,它将是一个IN子句

    <?xml version="1.0" encoding="UTF-8"?>
<root>
    <sets>
        <set>
            <set_no>1</set_no>
            <sub_sets>
                <sub_set>1</sub_set>
                <sub_set>2</sub_set>
                <sub_set>3</sub_set>
            </sub_sets>
        </set>
        <set>
            <set_no>2</set_no>
            <sub_sets>
                <sub_set>1</sub_set>
                <sub_set>3</sub_set>
            </sub_sets>
        </set>
    </sets>
    <book>
        <chapter>
            <section>
                <sec_no>1</sec_no>
                <sub_section>
                    <sub_sec>A</sub_sec>
                    <sub_sec>B</sub_sec>
                    <sub_sec>C</sub_sec>
                    <sub_sec>D</sub_sec>
                    <sub_sec>G</sub_sec>
                </sub_section>
            </section>
            <section>
                <sec_no>2</sec_no>
                <sub_section>
                    <sub_sec>E</sub_sec>
                    <sub_sec>F</sub_sec>
                </sub_section>
            </section>
        </chapter>
    </book>
</root>

我在XSLT1.0中坚持如何做到这一点

我这样做的方式是迭代集合,然后对每个集合进行迭代。这有效,直到需求更改为按sub_sec排序(因此对多个部分进行排序

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    <xsl:output method="html" doctype-public="-//W3C//DTD XHTML 1.0 Transitional//EN"
        doctype-system="http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"/>


    <xsl:template match="root">
        <html>
            <body>
                <xsl:for-each select="sets/set">
                    <xsl:variable name="curr_set" select="set_no"/> 
                    Set: <xsl:value-of select="$curr_set"/>
                    <br/>
                    <xsl:for-each select="sub_sets/sub_set">
                        <xsl:variable name="curr_sub_set" select="node()"/> 
                        <!--Curr-Sub-Set: <xsl:value-of select="$curr_sub_set"/><br/>-->
                        <xsl:for-each select="/root/book/chapter/section[sec_no=$curr_sub_set]/sub_section/sub_sec">
                            <xsl:value-of select="."/><br />
                        </xsl:for-each>
                    </xsl:for-each>
                    <br/><br/>
                </xsl:for-each>
            </body>
        </html>
    </xsl:template>
</xsl:stylesheet>

2 个答案:

答案 0 :(得分:1)

这应该有效:

<xsl:template match="root">
    <html>
        <body>
            <xsl:for-each select="sets/set">
                Set: <xsl:value-of select="set_no"/>
                <br/>
                <xsl:for-each select="/root/book/chapter/section[sec_no=current()/sub_sets/sub_set]/sub_section/sub_sec">
                    <xsl:sort select="."/>
                    <xsl:value-of select="."/><br />                    
                </xsl:for-each>
            </xsl:for-each>
        </body>
    </html>
</xsl:template>

这会产生:

Set: 1<br>A<br>B<br>C<br>D<br>E<br>F<br>G<br>
Set: 2<br>A<br>B<br>C<br>D<br>G<br>

根据您的要求订购输出。

在谓词表达式[sec_no=current()/sub_sets/sub_set]中,current()绑定到正在计算的 set ,因此current()/sub_sets/sub_set获取 sub_set 列表当前中的值。当 sec_no 在此列表中时,谓词将为真。

答案 1 :(得分:0)

使用key

可以最好地解决此类问题

XSLT 1.0

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

<xsl:key name="sub_sec-by-sec_no" match="sub_sec" use="ancestor::section/sec_no" />

<xsl:template match="/root">
    <html>
        <body>
            <xsl:for-each select="sets/set">
                Set: <xsl:value-of select="set_no"/>
                <br/>
                <xsl:for-each select="key('sub_sec-by-sec_no', sub_sets/sub_set)">
                    <xsl:sort select="." data-type="text" order="ascending"/>
                    <xsl:value-of select="."/>
                    <br/>
                </xsl:for-each>
                <br/><br/>
            </xsl:for-each>
        </body>
    </html>
</xsl:template>

</xsl:stylesheet>