极限XSLT XML扁平化

极限XSLT XML扁平化,xslt,flatten,Xslt,Flatten,我有以下输入XML文件: <root> <a> <b>1</b> </a> <c> <d> <e>2</e> <f>3</f> or <e>3</e> </d> <g h="4"/> <i> <j> <k>

我有以下输入XML文件:

<root>
 <a>
   <b>1</b>
 </a>
 <c>
   <d>
     <e>2</e>
     <f>3</f> or <e>3</e>
   </d>
  <g h="4"/>
  <i>
    <j>
      <k>
        <l m="5" n="6" o="7" />
        <l m="8" n="9" o="0" />
      </k>
    </j>
  </i>
 </c>
</root>

1.
2.
三三
我想使用XSLT将其转换为以下输出:

产出1

<root>
  <row b="1" e="2" f="3" h="4" m="5" n="6" o="7" />
  <row b="1" e="2" f="3" h="4" m="8" n="9" o="0" />
<root>

产出2

<root>
  <row b="1" e="2" h="4" m="5" n="6" o="7" />
  <row b="1" e="2" h="4" m="8" n="9" o="0" />
  <row b="1" e="3" h="4" m="5" n="6" o="7" />
  <row b="1" e="3" h="4" m="8" n="9" o="0" />
<root>


谁能帮我一下我的XSLT不是很强。谢谢。

如果让
的出现来决定构建
的外循环,并让一个内循环迭代所有
的话,这会更容易

试着这样做:

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

    <xsl:template match="/">
        <xsl:apply-templates />
    </xsl:template>

    <xsl:template match="root">
        <root>
            <xsl:apply-templates />
        </root>
    </xsl:template>

    <xsl:template match="e">
        <!-- store values of 'e' and 'f' in params -->
        <xsl:param name="value_of_e" select="." />
        <xsl:param name="value_of_f" select="ancestor::d[1]/f" />
        <!-- iterate over all 'l's -->
        <xsl:for-each select="//l">
            <xsl:element name="row">
                <xsl:attribute name="b">
                    <xsl:value-of select="//b" />
                </xsl:attribute>
                <xsl:attribute name="e">
                    <xsl:value-of select="$value_of_e" />
                </xsl:attribute>
                <!-- only include 'f' if it has a value -->
                <xsl:if test="$value_of_f != ''">
                    <xsl:attribute name="f">
                        <xsl:value-of select="$value_of_f" />
                    </xsl:attribute>
                </xsl:if>
                <xsl:attribute name="h">
                    <xsl:value-of select="ancestor::c[1]/g/@h" />
                </xsl:attribute>
                <xsl:attribute name="m">
                    <xsl:value-of select="./@m" />
                </xsl:attribute>
                <xsl:attribute name="n">
                    <xsl:value-of select="./@n" />
                </xsl:attribute>
                <xsl:attribute name="o">
                    <xsl:value-of select="./@o" />
                </xsl:attribute>
            </xsl:element>
        </xsl:for-each>
    </xsl:template>

    <xsl:template match="b" />
    <xsl:template match="f" />
    <xsl:template match="g" />
</xsl:stylesheet>


您是否需要2个XSLT文件,换句话说,执行2次转换?是的,我认为它们非常相似。因此,请您解释一下逻辑。转换由重复的元素l驱动,因此l=行。有来自其他元素和属性的值需要作为属性添加到行元素中。在第二个示例中,f是e,因此d下有两个e元素,因为行不能有两个同名的属性,所以第二个e需要有两个额外的行-我将编辑该示例。@David,这意味着行是由
的子级而不是
确定的。