如何使用xslt比较和合并两个xml
发布时间:2020-12-16 07:58:04 所属栏目:百科 来源:网络整理
导读:我想比较两个xmls然后合并它们.例如: myFile1.xml ?xml version="1.0" encoding="ISO-8859-1"?catalogdata titleTitle1/title descriptionDescription1/description myid1/myid/datadata titleTitle2/title descriptionDescription2/description myid2/myid
我想比较两个xmls然后合并它们.例如:
myFile1.xml <?xml version="1.0" encoding="ISO-8859-1"?> <catalog> <data> <title>Title1</title> <description>Description1</description> <myid>1</myid> </data> <data> <title>Title2</title> <description>Description2</description> <myid>2</myid> </data> </catalog> myFile2.xml <?xml version="1.0" encoding="ISO-8859-1"?> <catalog> <data> <title>Title1</title> <description>Description1</description> <author>Author1</author> <date>12/34/5678</date> <myid>1</myid> </data> <data> <author>Author2</author> <date>87/65/4321</date> <myid>2</myid> </data> </catalog> 期望的输出: <?xml version="1.0" encoding="ISO-8859-1"?> <catalog> <data> <title>Title1</title> <description>Description1</description> <myid>1</myid> <author>Author1</author> <date>12/34/5678</date> </data> <data> <title>Title2</title> <description>Description2</description> <myid>2</myid> <author>Author2</author> <date>87/65/4321</date> </data> </catalog> 我有一个代码,但它没有按照所需的输出执行. <?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="compare" select="'myFile1.xml'"/> <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="*"> <xsl:copy> <xsl:apply-templates select="@*|node()"/> <xsl:variable name="info1" select="document($compare)/catalog/data[myid=current()/myid]/."/> <xsl:variable name="info2" select="document($with)/catalog/data[myid=current()/myid]/."/> <xsl:for-each select="$info1/*"> <xsl:variable name="check1" select="name(current())"/> <!--xsl:text>Current node1 : </xsl:text><xsl:value-of select="$check1"/--> <xsl:for-each select="$info2/*"> <xsl:variable name="check2" select="name(current())"/> <!--xsl:text>Current node2 : </xsl:text><xsl:value-of select="$check2"/--> <xsl:if test="$check1!=$check2"> <xsl:copy-of select="."/> </xsl:if> </xsl:for-each> </xsl:for-each> </xsl:copy> </xsl:template> </xsl:transform> 请帮忙!
该解决方案完全没有循环或密钥.我只使用document()加载了一个文档,而另一个文档则作为源加载.简而言之,源文档中缺少一个元素,它是在加载的元素上获取的.更多可用的元素就是这个解决方案.请参阅底部以获得更一般的信息.
XSLT 1.0在Saxon-HE 9.2.1.1J上测试 <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:output omit-xml-declaration="yes" indent="yes"/> <xsl:strip-space elements="*"/> <xsl:variable name="catalog2" select="document('source_test2.xml')/catalog"/> <xsl:template match="catalog"> <catalog> <xsl:apply-templates select="data"/> </catalog> </xsl:template> <xsl:template match="data"> <xsl:variable name="data2" select="$catalog2/data[myid=current()/myid]/."/> <data> <xsl:choose> <xsl:when test="title"> <xsl:copy-of select="title"/> </xsl:when> <xsl:otherwise> <xsl:copy-of select="$data2/title"/> </xsl:otherwise> </xsl:choose> <xsl:choose> <xsl:when test="description"> <xsl:copy-of select="description"/> </xsl:when> <xsl:otherwise> <xsl:copy-of select="$data2/description"/> </xsl:otherwise> </xsl:choose> <xsl:copy-of select="myid"/> <xsl:choose> <xsl:when test="author"> <xsl:copy-of select="author"/> </xsl:when> <xsl:otherwise> <xsl:copy-of select="$data2/author"/> </xsl:otherwise> </xsl:choose> <xsl:choose> <xsl:when test="date"> <xsl:copy-of select="date"/> </xsl:when> <xsl:otherwise> <xsl:copy-of select="$data2/date"/> </xsl:otherwise> </xsl:choose> </data> </xsl:template> </xsl:stylesheet> 以下是一个更通用的解决方案.方法是一样的.对于每个数据,myFile2中存在且myFile1中缺少的元素将添加到结果树中,反之亦然. XSLT 1.0在Saxon-B 9.0.0.4J上测试 <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:output omit-xml-declaration="yes" indent="yes"/> <xsl:strip-space elements="*"/> <xsl:variable name="catalog2" select="document('myFile2.xml')/catalog"/> <xsl:template match="catalog"> <catalog> <xsl:apply-templates select="data"/> </catalog> </xsl:template> <xsl:template match="data"> <xsl:variable name="data1" select="."/> <xsl:variable name="data2" select="$catalog2/data[myid=current()/myid]/."/> <data> <xsl:copy-of select="$data1/*"/> <xsl:for-each select="$data2/*"> <xsl:variable name="element2" select="name(.)"/> <xsl:if test="count($data1/*[name()=$element2])=0"> <xsl:copy-of select="."/> </xsl:if> </xsl:for-each> </data> </xsl:template> </xsl:stylesheet> (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |