You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何使用XSLT合并两个结构相似的XML文件?

如何使用XSLT合并两个结构相似的XML文件?

看起来你想要合并两个结构相近的XML文件,核心需求是:对于reference相同的<common-indicator>条目,要把它们的<reports>内容合并到一起,而不是重复生成相同reference的条目。你原来的XSLT只是简单把两个文件的所有条目拼接,所以会出现重复的REF10,我来帮你调整代码实现正确的合并逻辑:

首先看你的主输入文件01.xml:

<?xml version="1.0" encoding="utf-8" standalone="yes"?>
<common-indicators>
  <common-indicator>
    <reference>REF01</reference>
    <name>name1</name>
    <reports>
      <report>
        <id>15</id>
        <name>name15</name>
      </report>
      <report>
        <id>16</id>
        <name>name16</name>
      </report>
    </reports>
  </common-indicator>
  <common-indicator>
    <reference>REF10</reference>
    <name>name10</name>
    <reports>
      <report>
        <id>30</id>
        <name>name30</name>
      </report>
      <report>
        <id>32</id>
        <name>name32</name>
      </report>
      <report>
        <id>34</id>
        <name>name34</name>
      </report>
    </reports>
  </common-indicator>
</common-indicators>

接下来是修改后的XSLT代码,它会处理主文件和参数传入的第二个XML,合并同reference的reports:

<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:xs="http://www.w3.org/2001/XMLSchema" exclude-result-prefixes="#all" version="3.0">
  <xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes" />
  
  <!-- 要合并的第二个XML文件,作为参数传入 -->
  <xsl:param name="param1">
    <common-indicators>
      <common-indicator>
        <reference>REF02</reference>
        <name>name2</name>
        <reports>
          <report>
            <id>17</id>
            <name>name17</name>
          </report>
          <report>
            <id>18</id>
            <name>name18</name>
          </report>
        </reports>
      </common-indicator>
      <common-indicator>
        <reference>REF10</reference>
        <name>name10</name>
        <reports>
          <report>
            <id>36</id>
            <name>name36</name>
          </report>
          <report>
            <id>38</id>
            <name>name38</name>
          </report>
          <report>
            <id>40</id>
            <name>name40</name>
          </report>
        </reports>
      </common-indicator>
    </common-indicators>
  </xsl:param>

  <!-- 定义key,按reference字段分组主文件和参数文件的条目 -->
  <xsl:key name="indicator-by-ref" match="common-indicator" use="reference"/>

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

  <xsl:template match="common-indicators">
    <xsl:copy>
      <!-- 处理主文件中的所有common-indicator -->
      <xsl:apply-templates select="common-indicator"/>
      <!-- 添加参数文件中主文件没有的common-indicator -->
      <xsl:apply-templates select="$param1/common-indicators/common-indicator[not(key('indicator-by-ref', reference, ..))]"/>
    </xsl:copy>
  </xsl:template>

  <!-- 处理common-indicator时,合并同reference的reports -->
  <xsl:template match="common-indicator">
    <xsl:copy>
      <xsl:apply-templates select="@*|node()[not(self::reports)]"/>
      <reports>
        <!-- 保留当前条目的reports -->
        <xsl:apply-templates select="reports/report"/>
        <!-- 添加参数文件中同reference条目的reports -->
        <xsl:apply-templates select="key('indicator-by-ref', reference, $param1/common-indicators)/reports/report"/>
      </reports>
    </xsl:copy>
  </xsl:template>
</xsl:stylesheet>

关键逻辑说明:

  • 用<xsl:key>定义了按reference分组的规则,方便快速找到同reference的条目
  • 处理主文件的<common-indicator>时,会把自身的reports和参数文件中同reference条目的reports合并在一起
  • 最后只添加参数文件中主文件没有的新common-indicator,避免重复

运行这个XSLT后,就能得到你想要的合并结果:

<?xml version="1.0" encoding="UTF-8"?>
<common-indicators>
  <common-indicator>
    <reference>REF01</reference>
    <name>name1</name>
    <reports>
      <report>
        <id>15</id>
        <name>name15</name>
      </report>
      <report>
        <id>16</id>
        <name>name16</name>
      </report>
    </reports>
  </common-indicator>
  <common-indicator>
    <reference>REF10</reference>
    <name>name10</name>
    <reports>
      <report>
        <id>30</id>
        <name>name30</name>
      </report>
      <report>
        <id>32</id>
        <name>name32</name>
      </report>
      <report>
        <id>34</id>
        <name>name34</name>
      </report>
      <report>
        <id>36</id>
        <name>name36</name>
      </report>
      <report>
        <id>38</id>
        <name>name38</name>
      </report>
      <report>
        <id>40</id>
        <name>name40</name>
      </report>
    </reports>
  </common-indicator>
  <common-indicator>
    <reference>REF02</reference>
    <name>name2</name>
    <reports>
      <report>
        <id>17</id>
        <name>name17</name>
      </report>
      <report>
        <id>18</id>
        <name>name18</name>
      </report>
    </reports>
  </common-indicator>
</common-indicators>

备注:内容来源于stack exchange,提问作者mancubus

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.04.20 10:28:10