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

如何用XSLT移除存在重复兄弟节点的XML节点?

XSLT移除重复文本的兄弟节点(含原节点与重复节点)

示例输入XML

假设你的XML结构如下(包含重复的Africa、Mexico节点):

<root>
  <row>Africa</row>
  <row>Africa</row>
  <row>Canada</row>
  <row>Mexico</row>
  <row>Mexico</row>
  <row>Brazil</row>
</root>

目标输出XML

仅保留无重复的节点:

<root>
  <row>Canada</row>
  <row>Brazil</row>
</root>

XSLT实现方案

方案1:XSLT 1.0(兼容旧版处理器)

利用Muenchian分组实现,核心是按文本内容分组,仅保留分组大小为1的节点:

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

  <!-- 按<row>的文本内容建立索引键 -->
  <xsl:key name="row-text-group" match="row" use="normalize-space(text())"/>

  <xsl:template match="root">
    <xsl:copy>
      <!-- 筛选:当前节点是分组首节点,且分组内仅一个节点 -->
      <xsl:copy-of select="row[
        generate-id() = generate-id(key('row-text-group', normalize-space(text()))[1])
        and count(key('row-text-group', normalize-space(text()))) = 1
      ]"/>
    </xsl:copy>
  </xsl:template>
</xsl:stylesheet>

方案2:XSLT 2.0及以上(更简洁)

利用原生分组语法,代码可读性更强:

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

  <xsl:template match="root">
    <xsl:copy>
      <!-- 按<row>文本分组,仅保留大小为1的分组 -->
      <xsl:for-each-group select="row" group-by="normalize-space(text())">
        <xsl:if test="current-group()[last()] = current-group()[1]">
          <xsl:copy-of select="current-group()"/>
        </xsl:if>
      </xsl:for-each-group>
    </xsl:copy>
  </xsl:template>
</xsl:stylesheet>

关键逻辑说明

  • 使用normalize-space(text())是为了忽略文本前后的空白,避免因空白差异误判为非重复;如果你的文本是严格无空白的,也可以直接用text()。
  • 核心思路是分组后过滤:将所有按文本内容分组,仅保留那些分组内只有一个节点的组——这样就同时移除了原重复节点和它的副本,只留下完全唯一的。

内容的提问来源于stack exchange,提问作者Hanu575

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.15 12:50:03