2012-08-31 80 views
2

我想在匹配'id'屬性時使用XSLT合併2個XML文件。使用XSLT合併2個匹配'id'屬性的XML文件

myFile1.xml(這是第一個輸入文件)

<?xml version="1.0" encoding="ISO-8859-1"?> 
    <test> 
     <node> 
     <type id="a"> 
      <name>joe</name> 
      <name>kill</name> 
     </type> 
     </node> 
     <node> 
     <type id="b"> 
      <name>sam</name> 
     </type> 
     </node> 
    </test> 

myFile2.xml(這是第二輸入文件)

<?xml version="1.0" encoding="ISO-8859-1"?> 
    <test> 
     <node> 
     <type id="a"> 
     <name>jill</name> 
     <name>kill</name> 
     </type> 
     </node> 
    </test> 

mergeOutput.xml(這是預期的輸出其中id匹配和2個文件被合併)

<?xml version="1.0" encoding="ISO-8859-1"?> 
    <test> 
     <node> 
     <type id="a"> 
      <name>joe</name> 
     <name>jill</name> 
      <name>Kill</name> 
     </type> 
     </node> 
     <node> 
     <type id="b"> 
      <name>sam</name> 
     </type> 
     </node> 
    </test> 

任何XSLT代碼或鏈接代碼將是有益的。我沒有XSLT知識並使用這種合併來使事情正常工作。

+0

可以有多個''在同一個文件中有'id'的元素? –

+0

(回覆Ian Roberts) - 文件中有多個元素,但每個元素都有唯一的id屬性。 –

+0

可以在幾秒鐘內使用LINQ2XML ...但不能在xslt中使用...可以使用LINQ2XML來處理這個IF#dev – Anirudha

回答

0
<?xml version="1.0" encoding="ISO-8859-1"?> 
<xsl:transform version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 
    <xsl:output method="xml" version="1.0" encoding="ISO-8859-1" indent="yes" /> 
    <xsl:variable name="with" select="'myFile2.xml'" /> 
    <xsl:template match="@*|node()"> 
    <xsl:copy> 
     <xsl:apply-templates select="@*|node()" /> 
    </xsl:copy> 
    </xsl:template> 

    <xsl:template match="//type"> 
    <xsl:copy> 
     <xsl:apply-templates select="@*|node()" /> 
     <xsl:variable name="info" select="document($with)/test/node/type[@id=current()/@id]/." /> 
    <xsl:for-each select="$info/*"> 
      <xsl:copy-of select="." /> 
     </xsl:for-each> 
    </xsl:copy> 
    </xsl:template> 
</xsl:transform> 

這樣做的這個變換的輸出是(見殺被複制) -

<?xml version="1.0" encoding="ISO-8859-1"?> 
<test> 
    <node> 
     <type id="a"> 
      <name>joe</name> 
      <name>kill</name> 
      <name>jill</name> 
      <name>kill</name> 
     </type> 
    </node> 
    <node> 
     <type id="b"> 
      <name>sam</name> 
     </type> 
    </node> 
</test> 
+0

我用上面的變換來獲取帶有重複項的中間XML,然後我寫了另一個來找到並刪除給定/ type/@ id下的重複項

0

XSLT 2.0解決方案:

<xsl:template name="main"> 
    <test> 
    <node> 
     <xsl:for-each-group select="(doc('myFile1.xml'), doc('myFile2.xml'))/test/node/type" 
          group-by="@id"> 
     <type id="{@id}"> 
      <xsl:copy-of select="current-group()/*"/> 
     </type> 
     </xsl:for-each-group> 
    </node> 
    </test> 
</xsl:template> 
0

可以在LINQ2XML

XElement doc1=XElement.Load("myFile1.xml"); 
XElement doc2=XElement.Load("myFile2.xml"); 
XElement doc3=XElement.Load("myFile1.xml");//will contain mergeOutput 

var dec=doc3.Descendants().Elements("type").ToList(); 
int i=0; 
foreach(XElement elm1 in doc1.Descendants().Elements("type")) 
foreach(XElement elm2 in doc2.Descendants().Elements("type")) 
if(elm1.Attribute("id").Value==elm2.Attribute("id").Value) 
dec[i++].Add(elm2.Elements()); 

doc3;//your mergeOutput 
+0

感謝您使用此解決方案,但由於架構考慮,我需要在XSLT中實現此功能。 –