将重复元素移动到其父元素的副本中



如果<animal>有超过 1 个<xxx>那么我需要复制<animal>(重复计数 = 相应<animal>内重复<xxx>计数)并将重复<xxx>移动到另一个副本中。

在我的 xml 中,<xxx><animal>的第一个实例重复两次,所以在输出中我需要有两个<animals>。第一个<animal>应包含<xxx>的第一个实例,第二个<animal>应包含第二个实例<xxx>

输入 xml

<?xml version="1.0" encoding="UTF-8"?>
<header>
    <animal>
        <element1>element1</element1>
        <element2>element2</element2>
        <element3 lang="en">element3</element3>
        <xxx>
            <code>YY</code>
            <description>code yy</description>
        </xxx>
        <xxx>
            <code>ZZ</code>
            <description>code zz</description>
        </xxx>
    </animal>
    <animal>
        <xxx>
            <code>AA</code>
            <description>code aa</description>
        </xxx>
    </animal>
</header>

所需的转换

<?xml version="1.0" encoding="UTF-8"?>
<header>
    <animal>
        <element1>element1</element1>
        <element2>element2</element2>
        <element3 lang="en">element3</element3>
        <xxx>
            <code>YY</code>
            <description>code yy</description>
        </xxx>        
    </animal>
    <animal>
        <element1>element1</element1>
        <element2>element2</element2>
        <element3 lang="en">element3</element3>        
        <xxx>
            <code>ZZ</code>
            <description>code zz</description>
        </xxx>
    </animal>
    <animal>
        <xxx>
            <code>AA</code>
            <description>code aa</description>
        </xxx>
    </animal>
</header>

任何帮助都非常感谢。提前致谢

我的解决方案通常不是最优雅的,但这会产生所需的输出 - 看看...

<?xml version="1.0" encoding="utf-8" standalone="yes"?>
<xsl:transform version="1.0" 
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform" >

<xsl:output method="xml" indent="yes"/>
<xsl:strip-space elements="*"/>
<xsl:template match="*|@*">
    <xsl:copy>
        <xsl:apply-templates select="*|@*|text()"/>
    </xsl:copy>
</xsl:template>
<xsl:template match="animal">
    <xsl:param name="i" select="xxx[1]"/>
    <xsl:variable name="thisanimal" select="."/>
    <xsl:choose>
        <xsl:when test="count(xxx) = 1">
            <!-- only one here -->
            <xsl:copy-of select="."/>
        </xsl:when>
        <xsl:when test="$i = xxx[1]">
            <!-- more than one here, use the first -->
            <xsl:copy>
                <xsl:apply-templates select="*[name() != 'xxx']"/>
                <xsl:apply-templates select="$i"/>
            </xsl:copy>
            <xsl:for-each select="xxx[position() &gt; 1]">
                <xsl:apply-templates select="$thisanimal">
                    <xsl:with-param name="i" select="."/>
                </xsl:apply-templates>
            </xsl:for-each>
        </xsl:when>
        <xsl:otherwise>
            <!-- more than one here -->
            <xsl:copy>
                <xsl:apply-templates select="*[name() != 'xxx']"/>
                <xsl:apply-templates select="$i"/>
            </xsl:copy>
        </xsl:otherwise>
    </xsl:choose>
</xsl:template>
</xsl:transform>

相关内容

  • 没有找到相关文章

最新更新