2017-01-09 58 views
0

我是XSLT新手,需要根据每个订单的ID总结项目的总价格(Quantity * UnitPrice),并使用XSLT 1.0将其打印在每个项目组的最后。 这是我的示例XMLXSLT分组和求和

<Orders> 
<Order> 
    <Reference>234</Reference> 
    <Item> 
     <ID>10</ID> 
     <Quantity>1</Quantity> 
     <UnitPrice>2</UnitPrice> 
    </Item> 
    <Item> 
     <ID>10</ID> 
     <Quantity>2</Quantity> 
     <UnitPrice>3</UnitPrice> 
    </Item> 
    <Item> 
     <ID>10</ID> 
     <Quantity>2</Quantity> 
     <UnitPrice>2</UnitPrice> 
    </Item> 
    <Item> 
     <ID>20</ID> 
     <Quantity>2</Quantity> 
     <UnitPrice>4</UnitPrice> 
    </Item> 
</Order> 
<Order> 
    <Reference>456</Reference> 
    <Item> 
     <ID>10</ID> 
     <Quantity>2</Quantity> 
     <UnitPrice>2</UnitPrice> 
    </Item> 
    <Item> 
     <ID>20</ID> 
     <Quantity>2</Quantity> 
     <UnitPrice>2</UnitPrice> 
    </Item> 
</Order> 
</Orders> 

所需的输出XML低于

<SAPOrders> 
<Order> 
    <Reference>234</Reference> 
    <Item> 
     <Quantity>1</Quantity> 
     <UnitPrice>2</UnitPrice> 
    </Item> 
    <Item> 
     <Quantity>2</Quantity> 
     <UnitPrice>3</UnitPrice> 
    </Item> 
    <Item> 
     <Quantity>2</Quantity> 
     <UnitPrice>2</UnitPrice> 
     <Total>12</Notes> 
    </Item> 
    <Item> 
     <Quantity>2</Quantity> 
     <UnitPrice>4</UnitPrice> 
     <Total>8</Notes> 
    </Item> 
</Order> 
<Order> 
    <Reference>456</Reference> 
    <Item> 
     <Quantity>2</Quantity> 
     <UnitPrice>2</UnitPrice> 
     <Total>4</Notes> 
    </Item> 
    <Item> 
     <Quantity>2</Quantity> 
     <UnitPrice>2</UnitPrice> 
     <Total>4</Total> 
    </Item> 
</Order> 
</SAPOrders> 
+0

参见http://stackoverflow.com/questions/37205574/sum-of-similar-elements-in-xslt这是一个近似重复 –

+1

@MichaelKay您指的是XSLT 2.0解决方案。 –

+1

@tojira为什么输出中没有项目ID? –

回答

0

这里有两个问题:(1)基团中的项目通过顺序由项目ID,和(2 )计算每个这样的组的小计。

第一个问题比较容易,可以使用Muenchian grouping方法解决。第二个问题更困难,因为XSLT 1.0不允许总结计算结果。

以下样式表首先预先计算每个项目的扩展价格并将结果存储在变量中。然后它对变量进行操作,对项目进行分组并对每个组进行小计。

XSLT 1.0

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

<xsl:key name="item" match="Item" use="@key" /> 

<xsl:template match="/Orders"> 
    <!-- first pass --> 
    <xsl:variable name="first-pass"> 
     <xsl:for-each select="Order"> 
      <Order> 
       <xsl:copy-of select="Reference"/> 
       <xsl:for-each select="Item"> 
        <Item key="{concat(../Reference, '|', ID)}" extPrice="{Quantity * UnitPrice}"> 
         <xsl:copy-of select="*"/> 
        </Item> 
       </xsl:for-each> 
      </Order> 
     </xsl:for-each> 
    </xsl:variable> 
    <!-- output --> 
    <SAPOrders> 
     <xsl:for-each select="exsl:node-set($first-pass)/Order"> 
      <xsl:copy> 
       <xsl:copy-of select="Reference"/> 
       <!-- for each unique item in this order --> 
       <xsl:for-each select="Item[count(. | key('item', @key)[1]) = 1]"> 
        <!-- list the items in this group --> 
        <xsl:for-each select="key('item', @key)"> 
         <Item> 
          <xsl:copy-of select="Quantity | UnitPrice"/> 
          <!-- add the subtotal of this group --> 
          <xsl:if test="position()=last()"> 
           <Total> 
            <xsl:value-of select="sum(key('item', @key)/@extPrice)" /> 
           </Total> 
          </xsl:if> 
         </Item> 
        </xsl:for-each> 
       </xsl:for-each> 
      </xsl:copy> 
     </xsl:for-each> 
    </SAPOrders> 
</xsl:template> 

</xsl:stylesheet> 

演示:http://xsltransform.net/jz1PuPz

+0

感谢您的解决方案!它运作良好! – tojira