2016-03-07 92 views
0

XSL让我疯狂,希望有人能帮助我解决这个问题。该代码已准备好复制粘贴。XSL 1.0组成元素总和1.0

我在XSL 1.0中做了一个分组,我希望对所有分组的'数量'元素进行求和。

我的数据看起来像这样。

<CustInvoiceTable class="entity"> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>0.05</Amount> 
     <ItemId>ITM-0000088</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>0.07</Amount> 
     <ItemId>ITM-0000088</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>0.16</Amount> 
     <ItemId>ITM-0000091</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>0.22</Amount> 
     <ItemId>ITM-0000091</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>1.33</Amount> 
     <ItemId>ITM-0000098</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>1.82</Amount> 
     <ItemId>ITM-0000098</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>0.01</Amount> 
     <ItemId>ITM-0000086</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>0.01</Amount> 
     <ItemId>ITM-0000086</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>0.05</Amount> 
     <ItemId>ITM-0000062</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>2</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>0.06</Amount> 
     <ItemId>ITM-0000062</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>2</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>0.02</Amount> 
     <ItemId>ITM-0000111</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>0.02</Amount> 
     <ItemId>ITM-0000111</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>0.06</Amount> 
     <ItemId>ITM-0000089</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>0.08</Amount> 
     <ItemId>ITM-0000089</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>1.96</Amount> 
     <ItemId>ITM-0000092</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>2.69</Amount> 
     <ItemId>ITM-0000092</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>0.07</Amount> 
     <ItemId>ITM-0000101</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>0.10</Amount> 
     <ItemId>ITM-0000101</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>0.07</Amount> 
     <ItemId>ITM-0000102</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>0.10</Amount> 
     <ItemId>ITM-0000102</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>6.69</Amount> 
     <ItemId>ITM-0000083</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>7.96</Amount> 
     <ItemId>ITM-0000083</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>0.15</Amount> 
     <ItemId>ITM-0000067</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>0.21</Amount> 
     <ItemId>ITM-0000067</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>1</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 

    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>96.00</Amount> 
     <ItemId>ITM-0000125</ItemId> 
     <McsCmBilProductItem class="entity"> 
      <CgiBundleLines>0</CgiBundleLines> 
     </McsCmBilProductItem> 
    </McsCmBilCalcInvoiceLine> 

    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>-88.00</Amount> 
     <ItemId>ITM-0000069</ItemId> 
    </McsCmBilCalcInvoiceLine> 

    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>-0.66</Amount> 
     <ItemId>ITM-0000083</ItemId> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>-0.22</Amount> 
     <ItemId>ITM-0000092</ItemId> 
    </McsCmBilCalcInvoiceLine> 
    <McsCmBilCalcInvoiceLine class="entity"> 
     <Amount>-0.55</Amount> 
     <ItemId>ITM-0000098</ItemId> 
    </McsCmBilCalcInvoiceLine> 

</CustInvoiceTable> 

而且XSL:

<xsl:stylesheet version="1.0" 
       xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 
    <xsl:key name="Lines-by-ItemId" match="CustInvoiceTable/McsCmBilCalcInvoiceLine" use="CustInvoiceTable/McsCmBilCalcInvoiceLine/ItemId" /> 

    <xsl:output method="xml" indent="yes" /> 

    <xsl:template match="/"> 

     <root> 

      <xsl:for-each select="CustInvoiceTable/McsCmBilCalcInvoiceLine[count(. | key('Lines-by-ItemId', ItemId)[1]) = 1][McsCmBilProductItem/CgiBundleLines = 1][not(ItemId = preceding-sibling::McsCmBilCalcInvoiceLine/ItemId)]"> 
       <xsl:sort select="ItemId" /> 
       <GroupInvoiceLine> 
        <ItemId><xsl:value-of select="ItemId" /></ItemId> 
        <SumAmount><xsl:value-of select="sum(Amount)"/></SumAmount> <!-- This does not work --> 
       </GroupInvoiceLine> 
      </xsl:for-each> 

     </root> 

    </xsl:template> 

</xsl:stylesheet> 

结果: 说,我们组的 “ITM-0000088” 我希望得到的结果是0.12。目前它只是抓住了第一个记录。

如果我们对“ITM-0000083”进行分组,我预计从上一个'ItemId = ITM-0000083'的'McsCmBilCalcInvoiceLine'开始,总和为6.69 + 7.96 = 14.65,而非6.69 + 7.96 + -0.66 = 13.99 'McsCmBilProductItem'中没有'CgiBundleLines = 1'。

+0

你有很多的代码在这里。请发布最小,完整,可验证的示例([MCVE](http://stackoverflow.com/help/mcve)) – MarkyPython

+0

是的 - 我将在下次减少数据量。谢谢。 – Lange

回答

0

定义键为<xsl:key name="Lines-by-ItemId" match="CustInvoiceTable/McsCmBilCalcInvoiceLine" use="ItemId" />,为use属性值是相对于匹配的节点计算的。

然后先看看如何使用密钥和Muenchian分组的,使用

 <xsl:for-each select="CustInvoiceTable/McsCmBilCalcInvoiceLine[count(. | key('Lines-by-ItemId', ItemId)[1]) = 1]"> 
      <xsl:sort select="ItemId" /> 
      <GroupInvoiceLine> 
       <ItemId><xsl:value-of select="ItemId" /></ItemId> 
       <SumAmount><xsl:value-of select="sum(key('Lines-by-ItemId', ItemId)/Amount)"/></SumAmount> 
      </GroupInvoiceLine> 
     </xsl:for-each> 

至于其他条件,可以考虑把它列入钥匙图案内:

<xsl:stylesheet version="1.0" 
       xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 
    <xsl:key name="Lines-by-ItemId" match="CustInvoiceTable/McsCmBilCalcInvoiceLine[McsCmBilProductItem/CgiBundleLines = 1]" use="ItemId" /> 

    <xsl:output method="xml" indent="yes" /> 

    <xsl:template match="/"> 

     <root> 

      <xsl:for-each select="CustInvoiceTable/McsCmBilCalcInvoiceLine[McsCmBilProductItem/CgiBundleLines = 1][count(. | key('Lines-by-ItemId', ItemId)[1]) = 1]"> 
       <xsl:sort select="ItemId" /> 
       <GroupInvoiceLine> 
        <ItemId><xsl:value-of select="ItemId" /></ItemId> 
        <SumAmount><xsl:value-of select="sum(key('Lines-by-ItemId', ItemId)/Amount)"/></SumAmount> 
       </GroupInvoiceLine> 
      </xsl:for-each> 

     </root> 

    </xsl:template> 

</xsl:stylesheet> 
+0

再次辉煌的工作。谢谢。 – Lange

0

首先,你的钥匙应该定义为:

<xsl:key name="Lines-by-ItemId" match="McsCmBilCalcInvoiceLine" use="ItemId" /> 

然后改变:

<SumAmount><xsl:value-of select="sum(Amount)"/></SumAmount> 

到:

<SumAmount><xsl:value-of select="sum(key('Lines-by-ItemId',ItemId)/Amount)"/></SumAmount> 
+0

这不会产生想要的结果。它没有考虑到只有'CgiBundleLines = 1'的行应该被分组。无论如何,谢谢。 – Lange

+0

@Lange您可以将谓词添加到正在求和的组中。 (同时询问多件事情不是一个好策略)。 –

+0

谢谢迈克尔。你可能是对的。我将来不会这样做。 – Lange