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

XSLT按Element拆分Segment求助:替换Statement1/2/3生成独立Statement

XSLT 转换问题排查与修正

问题需求

需要将输入XML中每个Statement1/Statement2/Statement3下的每个Cliam生成独立的Statement节点,同时将原Statement1/Statement2/Statement3替换为Statement。

输入示例

<?xml version="1.0" encoding="UTF-8"?>
<ns0:CustomerMas xmlns:ns0="http://123.com">
    <Statement1>
        <CustomerAssi_S_IM action="123">
            <table>CustomerAss_S_IM</table>
            <Cliam>
                <Field1>CM</Field1>
            </Cliam>
            <Cliam>
                <Field1>33</Field1>
                <Field2>31</Field2>
            </Cliam>
        </CustomerAssi_S_IM>
    </Statement1>
    <Statement2>
        <CustomerAssi_P_IM action="456">
            <table>second</table>
            <Cliam>
                <Field1>D4</Field1>
            </Cliam>
            <Cliam>
                <Field1>34</Field1>
                <Field2>31</Field2>
            </Cliam>
        </CustomerAssi_P_IM>
    </Statement2>
    <Statement3>
        <CustomerAssi_Q_IM action="789">
            <table>second</table>
            <Cliam>
                <Field1>D4</Field1>
            </Cliam>
        </CustomerAssi_Q_IM>
    </Statement3>
</ns0:CustomerMas>

期望输出示例

<?xml version="1.0" encoding="UTF-8"?>
<ns0:CustomerMas xmlns:ns0="http://123.com">
    <Statement>
        <CustomerAssi_S_IM action="123">
            <table>CustomerAss_S_IM</table>
            <Cliam>
                <Field1>CM</Field1>
            </Cliam>
        </CustomerAssi_S_IM>
    </Statement>
    <Statement>
        <CustomerAssi_S_IM action="123">
            <table>CustomerAss_S_IM</table>
            <Cliam>
                <Field1>33</Field1>
                <Field2>31</Field2>
            </Cliam>
        </CustomerAssi_S_IM>
    </Statement>
    <Statement>
        <CustomerAssi_P_IM action="456">
            <table>second</table>
            <Cliam>
                <Field1>D4</Field1>
            </Cliam>
        </CustomerAssi_P_IM>
    </Statement>
    <Statement>
        <CustomerAssi_P_IM action="456">
            <table>second</table>
            <Cliam>
                <Field1>34</Field1>
                <Field2>31</Field2>
            </Cliam>
        </CustomerAssi_P_IM>
    </Statement>
    <Statement>
        <CustomerAssi_Q_IM action="789">
            <table>second</table>
            <Cliam>
                <Field1>D4</Field1>
            </Cliam>
        </CustomerAssi_Q_IM>
    </Statement>
</ns0:CustomerMas>

原XSLT代码问题分析

  1. 命名空间错误:输入XML中Statement1/CustomerAssi_S_IM/Cliam等元素并未属于ns0命名空间(仅根元素ns0:CustomerMas使用该命名空间),但原XSLT中使用ns0:前缀匹配这些元素,导致for-each循环无法找到目标节点,输出不符合预期。
  2. 嵌套Statement标签:原模板在匹配Statement1/Statement2/Statement3时,先输出一个外层<Statement>,再在循环内输出内层<Statement>,最终会生成嵌套结构,与期望的平级Statement节点不符。
  3. 代码冗余:三个模板逻辑完全一致,仅元素名称不同,存在重复代码,可合并优化。

修正后的XSLT代码

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:ns0="http://123.com">
    <xsl:output method="xml" indent="yes" encoding="UTF-8"/>
    
    <!-- 身份转换模板,复制未匹配的节点 -->
    <xsl:template match="@*|node()">
        <xsl:copy>
            <xsl:apply-templates select="@*|node()"/>
        </xsl:copy>
    </xsl:template>
    
    <!-- 匹配所有Statement1/Statement2/Statement3节点 -->
    <xsl:template match="Statement1|Statement2|Statement3">
        <!-- 循环当前Statement下的所有Cliam节点 -->
        <xsl:for-each select="*/*/Cliam">
            <!-- 生成新的Statement节点 -->
            <Statement>
                <!-- 复制Cliam的祖父节点(如CustomerAssi_S_IM) -->
                <xsl:element name="{name(../..)}">
                    <!-- 复制祖父节点的所有属性 -->
                    <xsl:copy-of select="../..//@*"/>
                    <!-- 复制祖父节点下的table元素 -->
                    <xsl:copy-of select="../..//table"/>
                    <!-- 复制当前Cliam节点 -->
                    <xsl:copy-of select="."/>
                </xsl:element>
            </Statement>
        </xsl:for-each>
    </xsl:template>
</xsl:stylesheet>

修正说明

  • 移除了错误的ns0:前缀,确保能正确匹配目标元素;
  • 合并了三个重复的模板,通过Statement1|Statement2|Statement3匹配所有目标节点,减少冗余;
  • 去掉了外层嵌套的Statement标签,直接在循环内生成平级的Statement节点;
  • 使用动态元素名称{name(../..)}自动匹配父容器(如CustomerAssi_S_IM),无需硬编码元素名,提升通用性。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.13 07:32:06