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

基于XSLT 2.0实现多维度分组求和的技术求助

解决方案:XSLT 2.0 多维度分组汇总

问题背景

需在XSLT 2.0环境下,对交易数据按MemberID、DepositDate、DepositType进行三级分组,汇总每个分组的存款金额。此前使用的XSLT 3.0方案因环境限制无法兼容,需改用XSLT 2.0原生语法实现。

XML输入示例

<Transactions>
  <Transaction>
    <MemberID>M001</MemberID>
    <DepositDate>2024-01-01</DepositDate>
    <DepositType>定期</DepositType>
    <Amount>1000</Amount>
  </Transaction>
  <Transaction>
    <MemberID>M001</MemberID>
    <DepositDate>2024-01-01</DepositDate>
    <DepositType>活期</DepositType>
    <Amount>500</Amount>
  </Transaction>
  <Transaction>
    <MemberID>M001</MemberID>
    <DepositDate>2024-01-02</DepositDate>
    <DepositType>定期</DepositType>
    <Amount>2000</Amount>
  </Transaction>
  <Transaction>
    <MemberID>M002</MemberID>
    <DepositDate>2024-01-01</DepositDate>
    <DepositType>活期</DepositType>
    <Amount>1500</Amount>
  </Transaction>
</Transactions>

期望输出

<Summary>
  <MemberSummary MemberID="M001">
    <DateSummary DepositDate="2024-01-01">
      <TypeSummary DepositType="定期" TotalAmount="1000"/>
      <TypeSummary DepositType="活期" TotalAmount="500"/>
    </DateSummary>
    <DateSummary DepositDate="2024-01-02">
      <TypeSummary DepositType="定期" TotalAmount="2000"/>
    </DateSummary>
  </MemberSummary>
  <MemberSummary MemberID="M002">
    <DateSummary DepositDate="2024-01-01">
      <TypeSummary DepositType="活期" TotalAmount="1500"/>
    </DateSummary>
  </MemberSummary>
</Summary>

无效XSLT 3.0代码及问题

<xsl:stylesheet version="3.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
  <xsl:output method="xml" indent="yes"/>
  
  <xsl:template match="/Transactions">
    <Summary>
      <xsl:for-each-group select="Transaction" group-by="concat(MemberID, '|', DepositDate, '|', DepositType)">
        <MemberSummary MemberID="{current-grouping-key()[1]}">
          <DateSummary DepositDate="{current-grouping-key()[2]}">
            <TypeSummary DepositType="{current-grouping-key()[3]}" TotalAmount="{sum(current-group()/Amount)}"/>
          </DateSummary>
        </MemberSummary>
      </xsl:for-each-group>
    </Summary>
  </xsl:template>
</xsl:stylesheet>

问题:XSLT 2.0不支持current-grouping-key()的数组式访问,且单级分组拼接键值会导致重复生成MemberSummary和DateSummary节点,无法形成层级结构。

正确的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="/Transactions">
    <Summary>
      <!-- 第一级:按MemberID分组 -->
      <xsl:for-each-group select="Transaction" group-by="MemberID">
        <MemberSummary MemberID="{current-grouping-key()}">
          <!-- 第二级:当前会员组内按DepositDate分组 -->
          <xsl:for-each-group select="current-group()" group-by="DepositDate">
            <DateSummary DepositDate="{current-grouping-key()}">
              <!-- 第三级:当前日期组内按DepositType分组并汇总金额 -->
              <xsl:for-each-group select="current-group()" group-by="DepositType">
                <TypeSummary 
                  DepositType="{current-grouping-key()}" 
                  TotalAmount="{sum(current-group()/Amount)}"/>
              </xsl:for-each-group>
            </DateSummary>
          </xsl:for-each-group>
        </MemberSummary>
      </xsl:for-each-group>
    </Summary>
  </xsl:template>
</xsl:stylesheet>

说明:

  • 采用嵌套分组方式,依次按MemberID→DepositDate→DepositType层级分组,完全符合XSLT 2.0语法规范。
  • 使用current-group()获取当前分组内的所有节点,current-grouping-key()获取当前分组的键值。
  • 最内层分组通过sum(current-group()/Amount)计算该分组的总金额。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.03 14:12:44