如何从XSLT

时间:2016-04-14 08:59:24

标签: xml xslt

我需要通过XSLT Version 1.0合并两个XML文件。我的问题是,我需要将第二个XML文件的属性添加到第一个文件的属性中。让我举个例子来澄清我的问题。

XML1:

<sample>
  <tag a="1" b="2" c="3" d="4" />
  <tag a="2" b="3" c="4" d="5" />
</sample>

XML2:

<sample>
  <tag e="5" f="6" g="7" />
  <tag e="10" f="12" g="11" />
</sample>

输出:

<sample>
<tag a="1" b="2" c="3" d="4" e="5" f="6" g="7" />
<tag a="2" b="3" c="4" d="5" e="10" f="12" g="11" />
</sample>

我尝试了XSLT:

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:ws="http://www.w3schools.com">
<xsl:template match="/">                
 <xsl:for-each select="sample/tag">
<tag>
    <xsl:attribute name="a"><xsl:value-of select="@a"/></xsl:attribute>
    <xsl:attribute name="b"><xsl:value-of select="@b"/></xsl:attribute>
    <xsl:attribute name="c"><xsl:value-of select="@c"/></xsl:attribute>
    <xsl:attribute name="d"><xsl:value-of select="@d"/></xsl:attribute>
    <xsl:attribute name="e"><xsl:value-of select="document('xml2.xml')//@e"/></xsl:attribute>
    <xsl:attribute name="f"><xsl:value-of select="document('xml2.xml')//@f"/></xsl:attribute>
    <xsl:attribute name="g"><xsl:value-of select="document('xml2.xml')//@g"/></xsl:attribute>
<tag>
</xsl:for-each>

 </xbrl>
 </xsl:template>
 </xsl:stylesheet>

但我只获得了第二个XML文件的第一行。 EG我的输出是:

<sample>
<tag a="1" b="2" c="3" d="4" e="5" f="6" g="7" />
<tag a="2" b="3" c="4" d="5" e="5" f="6" g="7" />
</sample>

希望任何人都可以帮助我。我完全不熟悉XSLT。

2 个答案:

答案 0 :(得分:1)

一种简单易用的方法是使用以下模板应用一对一的位置映射:

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

<xsl:template match="tag">
  <xsl:variable name="pos" select="position()" />
  <tag>
    <xsl:copy-of select="@*" />
    <xsl:copy-of select="document('a2.xml')/sample/tag[$pos]/@*" />
  </tag>
</xsl:template>

输出为:

<?xml version="1.0"?>
<sample>
  <tag a="1" b="2" c="3" d="4" e="5" f="6" g="7"/>
  <tag a="2" b="3" c="4" d="5" e="10" f="12" g="11"/>
</sample>

答案 1 :(得分:0)

首先,您可以通过开始使用XSLT identity template来复制第一个XML中的现有节点和属性来简化操作

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

然后,要将额外属性添加到tag元素,您有一个匹配tag的模板

 <xsl:template match="tag">

在此,您需要获取当前元素的位置,以便在第二个文档中的相同位置找到相关的tag元素

<xsl:variable name="position">
    <xsl:number />
</xsl:variable>

然后,您可以从第二个文档中选择属性,如下所示:

<xsl:apply-templates select="document('xml2.xml')/sample/tag[position() = $position]/@*"/>

试试这个XSLT

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

    <xsl:template match="tag">
        <xsl:copy>
            <xsl:apply-templates select="@*"/>
            <xsl:variable name="position">
                <xsl:number />
            </xsl:variable>
            <xsl:apply-templates select="document('xml2.xml')/sample/tag[position() = $position]/@*"/>
            <xsl:apply-templates select="node()"/>
        </xsl:copy>
    </xsl:template>

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