Warning: file_get_contents(/data/phpspider/zhask/data//catemap/0/xml/15.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
使用XSLT将平面XML结构更改为层次结构_Xml_Xslt_Xpath - Fatal编程技术网

使用XSLT将平面XML结构更改为层次结构

使用XSLT将平面XML结构更改为层次结构,xml,xslt,xpath,Xml,Xslt,Xpath,我试图使用XSLT从平面XML文件创建分层XML文件,但不确定最佳方法是什么 e、 我需要转换 <root> <inventory bag="1" fruit="apple"/> <inventory bag="1" fruit="banana"/> <inventory bag="2" fruit="apple"/> <inventory bag="2" fruit="orange"/> </root> 到 对于N个袋子

我试图使用XSLT从平面XML文件创建分层XML文件,但不确定最佳方法是什么

e、 我需要转换

<root>
<inventory bag="1" fruit="apple"/>
<inventory bag="1" fruit="banana"/>
<inventory bag="2" fruit="apple"/>
<inventory bag="2" fruit="orange"/>
</root>

对于N个袋子/水果

xsl:your nodes两次,或者使用xsl:with不同的模式。

根据其袋子属性的值对库存元素进行分组:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    <xsl:key name="byBag" match="root/inventory" use="@bag" />
    <xsl:template match="/">
        <inventory>
            <baglist>
                <xsl:apply-templates mode="baglist" />
            </baglist>
            <xsl:apply-templates />
        </inventory>
    </xsl:template>
    <xsl:template
        match="root/inventory[generate-id() =
                             generate-id(key('byBag', @bag)[1])]" 
                        mode="baglist">
        <bag id="{@bag}" />
    </xsl:template>

    <xsl:template
        match="root/inventory[generate-id() =
                            generate-id(key('byBag', @bag)[1])]">
        <bag id="{@bag}">
            <xsl:apply-templates select="key('byBag', @bag)"
                mode="details" />
        </bag>
    </xsl:template>

    <xsl:template match="inventory" mode="details">
        <fruit id="{@fruit}" />
    </xsl:template>
</xsl:stylesheet>

谢谢,如果我理解正确,那么generate id将返回当前节点的唯一id,generate idkeystuff[1]将返回具有给定bagid的第一个节点的唯一id。这样,每个唯一的bagid只能有一个节点与模板匹配。@N.Shore-完全正确。然后,当我们将模板应用于键“byBag”时,@bag指定了一种模式,这样我们就可以处理组中的所有项目,而无需重新匹配只选择第一个项目的模板。这种技术被称为Muenchian分组方法。
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
    <xsl:key name="byBag" match="root/inventory" use="@bag" />
    <xsl:template match="/">
        <inventory>
            <baglist>
                <xsl:apply-templates mode="baglist" />
            </baglist>
            <xsl:apply-templates />
        </inventory>
    </xsl:template>
    <xsl:template
        match="root/inventory[generate-id() =
                             generate-id(key('byBag', @bag)[1])]" 
                        mode="baglist">
        <bag id="{@bag}" />
    </xsl:template>

    <xsl:template
        match="root/inventory[generate-id() =
                            generate-id(key('byBag', @bag)[1])]">
        <bag id="{@bag}">
            <xsl:apply-templates select="key('byBag', @bag)"
                mode="details" />
        </bag>
    </xsl:template>

    <xsl:template match="inventory" mode="details">
        <fruit id="{@fruit}" />
    </xsl:template>
</xsl:stylesheet>