在XSLT中将子/父链接添加到平面XML文件

在XSLT中将子/父链接添加到平面XML文件,xml,xslt,xslt-1.0,Xml,Xslt,Xslt 1.0,我有一个扁平的xml文档。这些节点确实包含指示它是父节点还是子节点的信息,并且子节点跟随其父节点的顺序是一致的。我需要一个XSLT文件来将输入xml转换为xml文件,其中子节点有一个指向其父节点的链接 输入XML文件: <items> <item type="a"> <value ID="11111" relation="parent"></value> </item> <item type

我有一个扁平的xml文档。这些节点确实包含指示它是父节点还是子节点的信息,并且子节点跟随其父节点的顺序是一致的。我需要一个XSLT文件来将输入xml转换为xml文件,其中子节点有一个指向其父节点的链接

输入XML文件:

<items>
    <item type="a">
        <value ID="11111" relation="parent"></value>
    </item>
    <item type="b">
        <value ID="22222" relation="child"></value>
    </item>
    <item type="b">
        <value ID="33333" relation="child"></value>
    </item>
    <item type="a">
        <value ID="44444" relation="parent"></value>
    </item>
    <item type="b">
        <value ID="55555" relation="child"></value>
    </item>
    <item type="a">
        <value ID="66666" relation="parent"></value>
    </item>
    <item type="a">
        <value ID="77777" relation="parent"></value>
    </item>
    <item type="b">
        <value ID="88888" relation="child"></value>
    </item>
    <item type="b">
        <value ID="99999" relation="child"></value>
    </item>
    <item type="b">
        <value ID="00000" relation="child"></value>
    </item>
</items>
我想把它转换成:

<items>
<item>
    <itemType>a</itemType>
    <itemID>11111</itemID>
    <itemRelationship>parent</itemRelationship>
    <itemParentID />
</item>
<item>
    <itemType>b</itemType>
    <itemID>22222</itemID>
    <itemRelationship>child</itemRelationship>
    <itemParentID>insert parent ID here</itemParentID>
</item>
<item>
    <itemType>b</itemType>
    <itemID>33333</itemID>
    <itemRelationship>child</itemRelationship>
    <itemParentID>insert parent ID here</itemParentID>
</item>
<item>
    <itemType>a</itemType>
    <itemID>44444</itemID>
    <itemRelationship>parent</itemRelationship>
    <itemParentID />
</item>
<item>
    <itemType>b</itemType>
    <itemID>55555</itemID>
    <itemRelationship>child</itemRelationship>
    <itemParentID>insert parent ID here</itemParentID>
</item>
<item>
    <itemType>a</itemType>
    <itemID>66666</itemID>
    <itemRelationship>parent</itemRelationship>
    <itemParentID />
</item>
<item>
    <itemType>a</itemType>
    <itemID>77777</itemID>
    <itemRelationship>parent</itemRelationship>
    <itemParentID />
</item>
<item>
    <itemType>b</itemType>
    <itemID>88888</itemID>
    <itemRelationship>child</itemRelationship>
    <itemParentID>insert parent ID here</itemParentID>
</item>
<item>
    <itemType>b</itemType>
    <itemID>99999</itemID>
    <itemRelationship>child</itemRelationship>
    <itemParentID>insert parent ID here</itemParentID>
</item>
<item>
    <itemType>b</itemType>
    <itemID>00000</itemID>
    <itemRelationship>child</itemRelationship>
    <itemParentID>insert parent ID here</itemParentID>
</item>
</items>
其中,“在此处插入父ID”由子节点的父ID替换

以下是我当前的xslt文件:

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

<xsl:template match="/">
    <items>
        <xsl:for-each select="items/item">
            <item>
                <xsl:variable name = "vCurrentItemType" select ="@type"/>
                <xsl:choose>
                    <xsl:when test = "$vCurrentItemType = 'a'">
                        <xsl:call-template name="DrawParent">
                            <xsl:with-param name = "pCurrentItem" select =  "current()"/>
                        </xsl:call-template>
                    </xsl:when>
                    <xsl:otherwise>
                        <xsl:call-template name="DrawChild">
                            <xsl:with-param name = "pCurrentItem" select = "current()"/>
                        </xsl:call-template>
                    </xsl:otherwise>
                </xsl:choose>
            </item>
        </xsl:for-each>
    </items>
</xsl:template>

<xsl:template name = "DrawParent">
    <xsl:param name = "pCurrentItem" />
    <itemType>
        <xsl:value-of select ="$pCurrentItem/@type"/>
    </itemType>
    <itemID>
        <xsl:value-of select ="$pCurrentItem/value/@ID"/>
    </itemID>
    <itemRelationship>
        <xsl:value-of select ="$pCurrentItem/value/@relation"/>
    </itemRelationship>
    <itemParentID></itemParentID>
</xsl:template>

<xsl:template name = "DrawChild">
    <xsl:param name = "pCurrentItem" />
    <itemType>
        <xsl:value-of select ="$pCurrentItem/@type"/>
    </itemType>
    <itemID>
        <xsl:value-of select ="$pCurrentItem/value/@ID"/>
    </itemID>
    <itemRelationship>
        <xsl:value-of select ="$pCurrentItem/value/@relation"/>
    </itemRelationship>
    <itemParentID>insert parent ID here</itemParentID>
</xsl:template>
</xsl:stylesheet>

您希望父ID的表达式为

<xsl:value-of select="$pCurrentItem/preceding-sibling::item[@type='a'][1]/value/@ID" />

但是,您可以考虑将XSLT简化为此,以避免某些代码重复……/P>

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="1.0">
    <xsl:output method="xml" indent="yes" />

    <xsl:template match="item">
       <item>
          <itemType>
              <xsl:value-of select="@type"/>
          </itemType>
          <itemID>
              <xsl:value-of select="value/@ID"/>
          </itemID>
          <itemRelationship>
              <xsl:value-of select="value/@relation"/>
          </itemRelationship>
          <itemParentID>
              <xsl:if test="@type='b'">
                    <xsl:value-of select="preceding-sibling::item[@type='a'][1]/value/@ID" />                  
              </xsl:if>
          </itemParentID>
       </item>
    </xsl:template>

    <xsl:template match="@*|node()">
        <xsl:copy>
            <xsl:apply-templates select="@*|node()"/>
        </xsl:copy>
    </xsl:template>
</xsl:stylesheet>