2015-10-24 80 views
-1

Combinig XML元素我想组基于特定节点值的XML:基于特定值

<bus:TaxList> 
<bus:VoPaidTax> 
<bus:TaxAmount>4.45</bus:TaxAmount> 
<bus:TaxCode>10</bus:TaxCode> 
<bus:TaxRate>0.05</bus:TaxRate> 
<bus:TaxType>VAT</bus:TaxType> 
</bus:VoPaidTax> 
<bus:VoPaidTax> 
<bus:TaxAmount>6.23</bus:TaxAmount> 
<bus:TaxCode>12</bus:TaxCode> 
<bus:TaxRate>0.07</bus:TaxRate> 
<bus:TaxType>VAT</bus:TaxType> 
</bus:VoPaidTax> 
<bus:VoPaidTax> 
<bus:TaxAmount>6.45</bus:TaxAmount> 
<bus:TaxCode>10</bus:TaxCode> 
<bus:TaxRate>0.05</bus:TaxRate> 
<bus:TaxType>VAT</bus:TaxType> 
</bus:VoPaidTax> 
<bus:VoPaidTax> 
<bus:TaxAmount>9.03</bus:TaxAmount> 
<bus:TaxCode>12</bus:TaxCode> 
<bus:TaxRate>0.07</bus:TaxRate> 
<bus:TaxType>VAT</bus:TaxType> 
</bus:VoPaidTax> 
</bus:TaxList 

现在我想添加具有相同TaxCode和速率VoPaidTax组。

<bus:TaxList> 
<bus:VoPaidTax> 
<bus:TaxAmount>10.90</bus:TaxAmount> 
<bus:TaxCode>10</bus:TaxCode> 
<bus:TaxRate>0.05</bus:TaxRate> 
<bus:TaxType>VAT</bus:TaxType> 
</bus:VoPaidTax> 
<bus:VoPaidTax> 
<bus:TaxAmount>15.23</bus:TaxAmount> 
<bus:TaxCode>12</bus:TaxCode> 
<bus:TaxRate>0.07</bus:TaxRate> 
<bus:TaxType>VAT</bus:TaxType> 
</bus:VoPaidTax> 
</bus:TaxList 

并留下唯一的。

我已经试过这样的事情,但它似乎不工作我在做什么错在这里:

<xsl:template match="bus:TaxList"> 
<xsl:for-each select="bus:VoPaidTax[not(bus:TaxCode = ../preceding- sibling::*/bus:VoPaidTax/bus:TaxCode) and not(bus:TaxRate= ../preceding- sibling::*/bus:VoPaidTax/bus:TaxRate)]"> 
<xsl:call-template name="taxCorrection"> 
<xsl:with-param name="TaxCode"> 
<xsl:value-of select="bus:TaxCode"/> 
</xsl:with-param> 
<xsl:with-param name="percent"> 
<xsl:value-of select="bus:TaxRate"/> 
</xsl:with-param> 
</xsl:call-template> 
</xsl:for-each> 
</xsl:template> 

<xsl:template name="taxCorrection"> 
<xsl:param name="TaxCode"/> 
<xsl:param name="percent"/> 
<xsl:variable name="sumTaxRate"> 
<xsl:value-of select="sum(../bus:VoPaidTax[bus:TaxCode = $TaxCode and bus:TaxRate =$percent]/bus:TaxAmount)" /> 
</xsl:variable> 

</xsl:template> 

事情是这样的模板被越来越多次调用和总和,以及前职业似乎不起作用。 我在这里做错了什么? 我正在使用XSLT 1.0 有人可以帮我一把!

+0

XSLT 1.0中的分组是通过称为Muenchian分组的方法实现的。阅读这篇文章:http://www.jenitennison.com/xslt/grouping/muenchian.html,看看已经发布在SO上的很多例子。 –

+0

我现在看到,我发布了几乎完全相同的评论上你以前的问题:http://stackoverflow.com/questions/32945177/grouping-xml-data-to-multiple-requests#comment53725311_32945177 –

+0

我认为Muenchian分组应该用于需要更快处理的地方。但是在这里,我总是会有更少的数据,而不是那么大的5-6个元素。我的方法在任何地方都不对 – Yauza

回答

1

事实上,考虑到Muenchian分组,特别是需要使用键来对齐组合数字。

<xsl:key name="taxgrp" match="bus:VoPaidTax" use="concat(bus:TaxCode, bus:TaxRate)" /> 

    <xsl:template match="bus:TaxList"> 
    <bus:TaxList>    
    <xsl:for-each select="bus:VoPaidTax[generate-id() 
       = generate-id(key('taxgrp', concat(bus:TaxCode, bus:TaxRate))[1])]"> 
     <bus:VoPaidTax> 
     <bus:TaxAmount> 
      <xsl:value-of select="sum(key('taxgrp', 
            concat(bus:TaxCode, bus:TaxRate))/bus:TaxAmount)"/> 
     </bus:TaxAmount> 
     <xsl:copy-of select="*[not(local-name()='bus:TaxAmount')]"/> 
     </bus:VoPaidTax> 
    </xsl:for-each>  
    </bus:TaxList> 
    </xsl:template>  

输出

<bus:TaxList> 
    <bus:VoPaidTax> 
    <bus:TaxAmount>10.9</bus:TaxAmount> 
    <bus:TaxCode>10</bus:TaxCode> 
    <bus:TaxRate>0.05</bus:TaxRate> 
    <bus:TaxType>VAT</bus:TaxType> 
    </bus:VoPaidTax> 
    <bus:VoPaidTax> 
    <bus:TaxAmount>15.26</bus:TaxAmount> 
    <bus:TaxCode>12</bus:TaxCode> 
    <bus:TaxRate>0.07</bus:TaxRate> 
    <bus:TaxType>VAT</bus:TaxType> 
    </bus:VoPaidTax> 
</bus:TaxList> 
+0

嗨Parfait我尝试了解您的解决方案和税额后更新我的问题与更新似乎给一些不同的价值,也TaxAmount出现两次。非常感谢你的帮助,直到现在。 – Yauza

0
<xsl:template match="@*|node()"> 
    <xsl:copy> 
     <xsl:apply-templates select="@*|node()" /> 
    </xsl:copy> 
</xsl:template> 
<xsl:key name="taxgrp" match="bus:VoPaidTax" use="concat(generate-id(..),bus:TaxCode, bus:TaxRate)" /> 

<xsl:template match="bus:BsAddOrderPaymentRequestPayload/bus:Request/bus:TotalPaidAmount/bus:TaxList"> 

<bus:TaxList>    
<xsl:for-each select="bus:VoPaidTax[generate-id() 
      = generate-id(key('taxgrp', concat(generate-id(..),bus:TaxCode, bus:TaxRate))[1])]"> 
    <bus:VoPaidTax> 
    <bus:TaxAmount> 
     <xsl:value-of select="sum(key('taxgrp', 
           concat(generate-id(..),bus:TaxCode, bus:TaxRate))/bus:TaxAmount)"/> 
    </bus:TaxAmount> 
    <xsl:copy-of select="*[not(self::bus:TaxAmount)]"/> 
    </bus:VoPaidTax> 
</xsl:for-each>  
</bus:TaxList> 
</xsl:template> 
</xsl:stylesheet> 

新增生成-ID(..)到每个键,以保持分组在特定的节点,而不是整个文档。