我如何使用键来转换它 [英] how can i transform this using keys

查看:23
本文介绍了我如何使用键来转换它的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我可以在不使用密钥的情况下编写非常糟糕的 xslt,但它非常缓慢且混乱.有谁知道我将如何将以下 XML 文件干净地转换为预期结果?谢谢!

I'm able to write a horribly bad xslt without using keys but it's quite slow and messy. Does anyone know how i would transform the following XML file into the expected result cleanly? Thanks!

输入:

<testExecution>
    <test>
        <test.1/>
        <test.2/>
        <test.3/>
    </test>
    <comment>
        <comment.1/>
        <comment.2/>
        <comment.3/>
    </comment>
    <executor>
        <executor.1/>
        <executor.2/>
        <executor.3/>
    </executor>
    <comment>
        <comment.1/>
        <comment.2/>
        <comment.3/>
    </comment>
    <comment>
        <comment.1/>
        <comment.2/>
        <comment.3/>
    </comment>
    <invoker>
        <invoker.1/>
        <invoker.2/>
        <invoker.3/>
    </invoker>
    <recipient>
        <recipient.1/>
        <recipient.2/>
        <recipient.3/>
    </recipient>
    <comment>
        <comment.1/>
        <comment.2/>
        <comment.3/>
    </comment>
    <comment>
        <comment.1/>
        <comment.2/>
        <comment.3/>
    </comment>
</testExecution>

结果:

<testExecution>
    <test>
        <test.1/>
        <test.2/>
        <test.3/>
    </test>
    <comment>
        <comment.1/>
        <comment.2/>
        <comment.3/>
    </comment>
    <people>
        <importantPeople>
            <executor>
                <executor.1/>
                <executor.2/>
                <executor.3/>
            </executor>
            <comment>
                <comment.1/>
                <comment.2/>
                <comment.3/>
            </comment>
            <comment>
                <comment.1/>
                <comment.2/>
                <comment.3/>
            </comment>
        </importantPeople>
        <invoker>
            <invoker.1/>
            <invoker.2/>
            <invoker.3/>
        </invoker>
    </people>
    <recipient>
        <recipient.1/>
        <recipient.2/>
        <recipient.3/>
    </recipient>
    <comment>
        <comment.1/>
        <comment.2/>
        <comment.3/>
    </comment>
    <comment>
        <comment.1/>
        <comment.2/>
        <comment.3/>
    </comment>
</testExecution>

推荐答案

此样式表:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    <xsl:key name="kElementByTest" match="invoker|recipient"
             use="generate-id(preceding-sibling::test[1])"/>
    <xsl:template match="node()|@*" name="identity">
        <xsl:copy>
            <xsl:apply-templates select="node()[1]|@*"/>
        </xsl:copy>
        <xsl:apply-templates select="following-sibling::node()[1]"/>
    </xsl:template>
    <xsl:template match="executor">
        <xsl:variable name="vFollowing"
                      select="key('kElementByTest',
                                  generate-id(preceding-sibling::test[1]))"/>
        <people>
            <importantPeople>
                <xsl:call-template name="identity"/>
            </importantPeople>
            <xsl:apply-templates select="$vFollowing/self::invoker"
                                     mode="copy"/>
        </people>
        <xsl:apply-templates select="$vFollowing/self::recipient"
                             mode="copy"/>
    </xsl:template>
    <xsl:template match="invoker"/>
    <xsl:template match="recipient"/>
    <xsl:template match="node()" mode="copy">
        <xsl:call-template name="identity"/>
    </xsl:template>
</xsl:stylesheet>

输出:

<testExecution>
    <test>
        <test.1></test.1>
        <test.2></test.2>
        <test.3></test.3>
    </test>
    <comment>
        <comment.1></comment.1>
        <comment.2></comment.2>
        <comment.3></comment.3>
    </comment>
    <people>
        <importantPeople>
            <executor>
                <executor.1></executor.1>
                <executor.2></executor.2>
                <executor.3></executor.3>
            </executor>
            <comment>
                <comment.1></comment.1>
                <comment.2></comment.2>
                <comment.3></comment.3>
            </comment>
            <comment>
                <comment.1></comment.1>
                <comment.2></comment.2>
                <comment.3></comment.3>
            </comment>
        </importantPeople>
        <invoker>
            <invoker.1></invoker.1>
            <invoker.2></invoker.2>
            <invoker.3></invoker.3>
        </invoker>
    </people>
    <recipient>
        <recipient.1></recipient.1>
        <recipient.2></recipient.2>
        <recipient.3></recipient.3>
    </recipient>
    <comment>
        <comment.1></comment.1>
        <comment.2></comment.2>
        <comment.3></comment.3>
    </comment>
    <comment>
        <comment.1></comment.1>
        <comment.2></comment.2>
        <comment.3></comment.3>
    </comment>
</testExecution>

注意:细粒度遍历.仅用于此测试"的键如下.关闭此级别"的空模板.推送样式保持处理"的模式.可以是完整的拉式"匹配标记前的上一个".

Note: Fine grained traversal. Keys for "just for this test" followings. Empty templates for "close this level". Mode for push style "keep processing". It could be full "pull style" matching "the previus before the mark".

这篇关于我如何使用键来转换它的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆