首页 > 解决方案 > 用子节点值分组并将分组的值相加一次

问题描述

我有一个像下面这样的场景,我想用子元素值对元素进行分组并总结数量。使用 xslt 1.0。

Input:
<body>
    <Root1>
        <Root2>
            <E1>abc</merchantcode>
            <C1>
                <order>
                    <catalog>
                        <catalogitem>100</catalogitem>
                        <sku>100</sku>
                        <quantity>1</quantity>
                    </catalog>
                </order>
            </C1>
            <C1>
                <order>
                    <catalog>
                        <catalogitem>100</catalogitem>
                        <sku>100</sku>
                        <quantity>2</quantity>
                    </catalog>
                </order>
            </C1>
            <C1>
                <order>
                    <catalog>
                        <catalogitem>111</catalogitem>
                        <sku>111</sku>
                        <quantity>1</quantity>
                    </catalog>
                </order>
            </C1>
        </Root2>
    </Root1>
</body>

我想根据 sku 值对上述 XML 文档进行分组。然后想总结数量。这是我想要的结果:

<body>
    <Root1>
        <Root2>
            <E1>abc</merchantcode>
            <C1>
                <order>
                    <catalog>
                        <catalogitem>100</catalogitem>
                        <sku>100</sku>
                        <quantity>3</quantity>
                    </catalog>
                </order>
            </C1>
            <C1>
                <order>
                    <catalog>
                        <catalogitem>111</catalogitem>
                        <sku>111</sku>
                        <quantity>1</quantity>
                    </catalog>
                </order>
            </C1>
        </Root2>
    </Root1>
</body>

谁可以帮我这个事?

标签: xsltxslt-2.0

解决方案


试试这种方式:

XSLT 2.0

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

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

<xsl:template match="Root2">
    <xsl:copy> 
        <xsl:apply-templates select="* except C1"/>
        <xsl:for-each-group select="C1" group-by="order/catalog/sku"> 
            <C1>
                <order>
                    <catalog>
                        <xsl:copy-of select="order/catalog/(catalogitem | sku)" /> 
                        <quantity>
                            <xsl:value-of select="sum(current-group()/order/catalog/quantity)" /> 
                        </quantity>
                    </catalog>
                </order>
            </C1>
        </xsl:for-each-group>
    </xsl:copy>
</xsl:template>

</xsl:stylesheet>

推荐阅读