与另一个 xml 文件相比,使记录的元素唯一

make an element of a record unique, compared to another xml file

给定两个 xml 文件,我需要比较 TITLEID 和 ARTIST 的组合是否唯一(这意味着在第二个文件中没有相同的 TITLEID、ARTIST 组合存在于第一个 xml 文件)

<CATALOG>
        <RECORD ID="109">
           <TITLEID>54</TITLEID>
           <ARTIST>Bob Dylan</ARTIST>
           <COUNTRY>USA</COUNTRY>
           <COMPANY>Columbia</COMPANY>
           <PRICE>10.90</PRICE>
           <YEAR>1985</YEAR> </CD>
        </RECORD>
        <RECORD ID="187">
           <TITLEID>88</TITLEID>
           <ARTIST>Bonnie Tyler</ARTIST>
           <COUNTRY>UK</COUNTRY>
           <COMPANY>CBS Records</COMPANY>
           <PRICE>9.90</PRICE>
           <YEAR>1988</YEAR> </CD>
         </RECORD>
    </CATALOG>

    second xml:

<CATALOG>
    <RECORD ID="109">
       <TITLEID>54</TITLEID>
       <ARTIST>Bob Dylan</ARTIST>
       <COUNTRY>USA</COUNTRY>
       <COMPANY>Columbia</COMPANY>
       <PRICE>10.90</PRICE>
       <YEAR>1985</YEAR> </CD>
    </RECORD>
     <RECORD ID="187">
       <TITLEID>text ',.</TITLEID>
       <ARTIST>Bonnie Tyler</ARTIST>
       <COUNTRY>UK</COUNTRY>
       <COMPANY>CBS Records</COMPANY>
       <PRICE>9.90</PRICE>
       <YEAR>1988</YEAR> </CD>
     </RECORD>
</CATALOG>

所以我需要执行以下操作,仅针对满足以下条件的那些记录: TITLEIDARTIST(来自 xml1)TITLEIDARTIST(来自 xml2)

我需要使 TITLEIDARTIST 组合唯一,在第一个 xml 文件中,例如向 TITLEID 添加一个数字(确保这个数字添加不会产生一个新数字,从而创建一个将匹配第二个 xml).

的新组合

所以期望的输出就像(我只需要修改第一个 xml,第二个保持不变):

<CATALOG>
        <RECORD ID="109">
           <TITLEID>540</TITLEID>
           <ARTIST>Bob Dylan</ARTIST>
           <COUNTRY>USA</COUNTRY>
           <COMPANY>Columbia</COMPANY>
           <PRICE>10.90</PRICE>
           <YEAR>1985</YEAR> </CD>
        </RECORD>
         <RECORD ID="187">
           <TITLEID>88</TITLEID>
           <ARTIST>Bonnie Tyler</ARTIST>
           <COUNTRY>UK</COUNTRY>
           <COMPANY>CBS Records</COMPANY>
           <PRICE>9.90</PRICE>
           <YEAR>1988</YEAR> </CD>
         </RECORD>
    </CATALOG>

请注意,在第二个 XML 文件的 TITLEID 中,可能会找到文本,而不仅仅是数字。

借助 XSLT 3,您可以使用复合键来识别辅助文档中存在重复项的元素,然后根据 generate-id():

生成新的 ID
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:xs="http://www.w3.org/2001/XMLSchema"
    exclude-result-prefixes="#all"
    expand-text="yes"
    version="3.0">

  <xsl:param name="doc2">
<CATALOG>
    <RECORD ID="109">
       <TITLEID>54</TITLEID>
       <ARTIST>Bob Dylan</ARTIST>
       <COUNTRY>USA</COUNTRY>
       <COMPANY>Columbia</COMPANY>
       <PRICE>10.90</PRICE>
       <YEAR>1985</YEAR>
    </RECORD>
     <RECORD ID="187">
       <TITLEID>text ',.</TITLEID>
       <ARTIST>Bonnie Tyler</ARTIST>
       <COUNTRY>UK</COUNTRY>
       <COMPANY>CBS Records</COMPANY>
       <PRICE>9.90</PRICE>
       <YEAR>1988</YEAR>
     </RECORD>
</CATALOG>      
  </xsl:param>

  <xsl:mode on-no-match="shallow-copy"/>

  <xsl:key name="ref" match="RECORD" composite="yes" use="TITLEID, ARTIST"/>

  <xsl:template match="RECORD[key('ref', (TITLEID, ARTIST), $doc2)]/TITLEID">
      <xsl:copy>{generate-id()}</xsl:copy>
  </xsl:template>

</xsl:stylesheet>

https://xsltfiddle.liberty-development.net/bnnZVZ/0

为了紧凑和自包含,该示例包括内联辅助文档,但当然您可以使用参数从外部传入文档或更改代码以使用例如<xsl:param name="doc2" select="doc($doc2-uri)"/> 带有第二个参数以传入第二个文档的 URI/location 例如<xsl:param name="doc2-uri" as="xs:string">second-doc.xml</xsl:param>.