2011-11-22 35 views
0

我有下面的XMLXSLT分组与子元素的添加/组合

<InvestmentAccount Id="Element01_Source3_Sequqence002" Type="Standard" InvestmentStrategyId="Employer" ParameterOverrideIds="AllocationRateOverride"> 
     <Investment FundName="Fund032" FundValue="4754.82" /> 
     <Investment FundName="Fund034" FundValue="4643.48" /> 
     <Investment FundName="Fund035" FundValue="2509.46" /> 
     <Investment FundName="Fund038" FundValue="7104.71" /> 
     <Investment FundName="Fund042" FundValue="4244.08" /> 
    </InvestmentAccount> 
    <InvestmentAccount Id="Element01_Source4_Sequence003" Type="DWPRebate" InvestmentStrategyId="DSS" ParameterOverrideIds="DWPAllocationRateOverride"> 
     <Investment FundName="Fund032" FundValue="1881.76" /> 
     <Investment FundName="Fund034" FundValue="1584.18" /> 
     <Investment FundName="Fund035" FundValue="872.99" /> 
     <Investment FundName="Fund038" FundValue="2899.53" /> 
     <Investment FundName="Fund042" FundValue="1762.62" /> 
    </InvestmentAccount> 
    <InvestmentAccount Id="Element01_Source2_Sequence001" Type="Standard" InvestmentStrategyId="Employee" ParameterOverrideIds="AllocationRateOverride"> 
     <Investment FundName="Fund032" FundValue="7395.91" /> 
     <Investment FundName="Fund034" FundValue="7222.72" /> 
     <Investment FundName="Fund035" FundValue="3903.52" /> 
     <Investment FundName="Fund038" FundValue="11051.32" /> 
     <Investment FundName="Fund042" FundValue="6602.54" /> 
    </InvestmentAccount> 
    <InvestmentAccount Id="Element02_Source2_Sequence004" Type="TransferNonPR" InvestmentStrategyId="Employee" ParameterOverrideIds="AllocationRateOverride"> 
     <Investment FundName="Fund032" FundValue="1439.29" /> 
     <Investment FundName="Fund034" FundValue="1614.31" /> 
     <Investment FundName="Fund035" FundValue="863.68" /> 
     <Investment FundName="Fund038" FundValue="2153.80" /> 
     <Investment FundName="Fund042" FundValue="1306.45" /> 
    </InvestmentAccount> 
    <InvestmentAccount Id="Element03_Source2_Sequence005" Type="TransferNonPR" InvestmentStrategyId="Employee" ParameterOverrideIds="AllocationRateOverride"> 
     <Investment FundName="Fund032" FundValue="9617.42" /> 
     <Investment FundName="Fund034" FundValue="10787.03" /> 
     <Investment FundName="Fund035" FundValue="5771.18" /> 
     <Investment FundName="Fund038" FundValue="14391.20" /> 
     <Investment FundName="Fund042" FundValue="8729.81" /> 
     <Investment FundName="fictiousextra" FundValue="1414" /> 
    </InvestmentAccount> 

我希望做的是在那里InvestmentStrategyId和类型相同,是与上面的最后2的情况下(为了清晰起见重新排序)是FundName与基金价值总和相同的地方。在这种情况下,每边都有相同的情况,但每边可能会多出一些或少一些。

所以结果是我需要访问FundName和FundValue或者我可以总结一个或者已经总结的值。

帮助!

对,所以这是我试图实现的输出。

 <InvestmentAccount Id="Element01_Source3_Sequence002" Type="Standard" InvestmentStrategyId="Employer" ParameterOverrideIds="AllocationRateOverride"> 
      <Investment FundName="Fund032" FundValue="4754.82" /> 
      <Investment FundName="Fund034" FundValue="4643.48" /> 
      <Investment FundName="Fund035" FundValue="2509.46" /> 
      <Investment FundName="Fund038" FundValue="7104.71" /> 
      <Investment FundName="Fund042" FundValue="4244.08" /> 
     </InvestmentAccount> 
     <InvestmentAccount Id="Element01_Source4_Sequence003" Type="DWPRebate" InvestmentStrategyId="DSS" ParameterOverrideIds="DWPAllocationRateOverride"> 
      <Investment FundName="Fund032" FundValue="1881.76" /> 
      <Investment FundName="Fund034" FundValue="1584.18" /> 
      <Investment FundName="Fund035" FundValue="872.99" /> 
      <Investment FundName="Fund038" FundValue="2899.53" /> 
      <Investment FundName="Fund042" FundValue="1762.62" /> 
     </InvestmentAccount> 
     <InvestmentAccount Id="Element01_Source2_Sequence001" Type="Standard" InvestmentStrategyId="Employee" ParameterOverrideIds="AllocationRateOverride"> 
      <Investment FundName="Fund032" FundValue="7395.91" /> 
      <Investment FundName="Fund034" FundValue="7222.72" /> 
      <Investment FundName="Fund035" FundValue="3903.52" /> 
      <Investment FundName="Fund038" FundValue="11051.32" /> 
      <Investment FundName="Fund042" FundValue="6602.54" /> 
     </InvestmentAccount> 
<!-- THIS ONE IS THE SUMMED COMBINTION DUE TO InvestmentStrategyId and Type being multiply occuring --> 
<InvestmentAccount ...> 
      <Investment FundName="Fund032" FundValue="11056.71" /> 
      <Investment FundName="Fund034" FundValue="12401.34" /> 
      <Investment FundName="Fund035" FundValue="6634.86" /> 
      <Investment FundName="Fund038" FundValue="16545" /> 
      <Investment FundName="Fund042" FundValue="10036.26" /> 
      <Investment FundName="fictiousextra" FundValue="1414" /> 
</InvestmentAccount> 

包括存在于1中而不是其他中的任何FundNames。

我要补充,我使用.NET 4.0

+0

你能提供一些输出吗?不知道你想做什么。 – FailedDev

回答

1

XSLT 2.0上运行的解决方案:

<?xml version="1.0" encoding="UTF-8"?> 
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" 
    xmlns:xs="http://www.w3.org/2001/XMLSchema" 
    exclude-result-prefixes="xs" 
    version="2.0"> 
    <xsl:template match="/"> 
     <xsl:apply-templates/> 
    </xsl:template> 
    <xsl:template match="*"> 
     <xsl:copy> 
      <xsl:copy-of select="@*"/> 
      <xsl:apply-templates/> 
     </xsl:copy> 
    </xsl:template> 
    <xsl:template match="InvestmentAccount[1]"> 
     <xsl:for-each-group select="self::*|following-sibling::InvestmentAccount" group-by="concat(@InvestmentStrategyId,@Type)" > 
      <InvestmentAccount Id="{@Id}" Type="{@Type}" InvestmentStrategyId="{@InvestmentStrategyId}" ParameterOverrideIds="{@ParameterOverrideIds}"> 
       <xsl:for-each-group select="current-group()/Investment" group-by="@FundName"> 
        <Investment FundName="{current-grouping-key()}" FundValue="{sum(for $x in current-group()/@FundValue return xs:double(data($x)))}" /> 
       </xsl:for-each-group> 
      </InvestmentAccount> 
     </xsl:for-each-group> 
    </xsl:template> 
    <xsl:template match="InvestmentAccount"/> 
</xsl:stylesheet> 

我插入你的XML在一个名为<test></test>根和XSLT的结果是:

<?xml version="1.0" encoding="UTF-8"?> 
<test> 
    <InvestmentAccount Id="Element01_Source3_Sequence002" Type="Standard" 
     InvestmentStrategyId="Employer" ParameterOverrideIds="AllocationRateOverride"> 
     <Investment FundName="Fund032" FundValue="4754.82"/> 
     <Investment FundName="Fund034" FundValue="4643.48"/> 
     <Investment FundName="Fund035" FundValue="2509.46"/> 
     <Investment FundName="Fund038" FundValue="7104.71"/> 
     <Investment FundName="Fund042" FundValue="4244.08"/> 
    </InvestmentAccount> 
    <InvestmentAccount Id="Element01_Source4_Sequence003" Type="DWPRebate" 
     InvestmentStrategyId="DSS" ParameterOverrideIds="DWPAllocationRateOverride"> 
     <Investment FundName="Fund032" FundValue="1881.76"/> 
     <Investment FundName="Fund034" FundValue="1584.18"/> 
     <Investment FundName="Fund035" FundValue="872.99"/> 
     <Investment FundName="Fund038" FundValue="2899.53"/> 
     <Investment FundName="Fund042" FundValue="1762.62"/> 
    </InvestmentAccount> 
    <InvestmentAccount Id="Element01_Source2_Sequence001" Type="Standard" 
     InvestmentStrategyId="Employee" ParameterOverrideIds="AllocationRateOverride"> 
     <Investment FundName="Fund032" FundValue="7395.91"/> 
     <Investment FundName="Fund034" FundValue="7222.72"/> 
     <Investment FundName="Fund035" FundValue="3903.52"/> 
     <Investment FundName="Fund038" FundValue="11051.32"/> 
     <Investment FundName="Fund042" FundValue="6602.54"/> 
    </InvestmentAccount> 
    <InvestmentAccount Id="Element02_Source2_Sequence004" Type="TransferNonPR" 
     InvestmentStrategyId="Employee" ParameterOverrideIds="AllocationRateOverride"> 
     <Investment FundName="Fund032" FundValue="11056.71"/> 
     <Investment FundName="Fund034" FundValue="12401.34"/> 
     <Investment FundName="Fund035" FundValue="6634.860000000001"/> 
     <Investment FundName="Fund038" FundValue="16545"/> 
     <Investment FundName="Fund042" FundValue="10036.26"/> 
     <Investment FundName="fictiousextra" FundValue="1414"/> 
    </InvestmentAccount> 




</test> 

注意:InvestmentAccount属性值是InvestmentAccount组中具有相同Type和Investm值的第一个元素InvestmentAccount之一entStrategyId。这可以很容易地改变。

+0

这看起来很刺眼,但不幸的是我正在运行使用.net所以只有1.0 :( –

+1

尝试使用撒克逊。我认为有一个.NET的实现。请参阅http://saxon.sourceforge.net/#F9.3HE(它的开源它是一个xslt 2.0处理器) –

1

XSLT 1.0将使用Muenchian分组。

我认为在这种情况下,你是分组两次。首先你被InvestmentAccount元素分组,所以你需要像这样

<xsl:key name="Accounts" match="InvestmentAccount" 
     use="concat(@Type, '|', @InvestmentStrategyId)" /> 

一个键,然后,你还需要GROUP BY 投资账户内元素。

<xsl:key name="Investments" match="Investment" 
     use="concat(../@Type, '|', ../@InvestmentStrategyId, '|', @FundName)" /> 

请注意在连接中使用管道。这可以是任何字符,但它必须是不具有任何属性的特征。通过InvestmentAccount元素

分组,然后你可以只是比赛的第一个元素每组如下所示:

<xsl:apply-templates 
    select="InvestmentAccount[ 
    generate-id() = 
    generate-id(key('Accounts', concat(@Type, '|', @InvestmentStrategyId))[1])]" /> 
组中

一旦,你可以得到所有的投资元素,如所以:

<xsl:apply-templates 
    select="//InvestmentAccount 
    [@Type=current()/@Type] 
    [@InvestmentStrategyId = current()/@InvestmentStrategyId]/Investment 
     [generate-id() = 
     generate-id(key('Investments', 
      concat(../@Type, '|', ../@InvestmentStrategyId, '|', @FundName))[1])]" /> 

以下是完整的XSLT(请注意,我假定称为根元素投资

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

    <xsl:key name="Accounts" match="InvestmentAccount" use="concat(@Type, '|', @InvestmentStrategyId)" /> 
    <xsl:key name="Investments" match="Investment" use="concat(../@Type, '|', ../@InvestmentStrategyId, '|', @FundName)" /> 

    <xsl:template match="/Investments"> 
     <xsl:apply-templates select="InvestmentAccount[generate-id() = generate-id(key('Accounts', concat(@Type, '|', @InvestmentStrategyId))[1])]" /> 
    </xsl:template> 

    <xsl:template match="InvestmentAccount"> 
     <xsl:copy> 
     <xsl:copy-of select="@*" /> 
     <xsl:apply-templates select="//InvestmentAccount[@Type=current()/@Type][@InvestmentStrategyId = current()/@InvestmentStrategyId]/Investment[generate-id() = generate-id(key('Investments', concat(../@Type, '|', ../@InvestmentStrategyId, '|', @FundName))[1])]" /> 
     </xsl:copy> 
    </xsl:template> 

    <xsl:template match="Investment"> 
     <xsl:copy> 
     <xsl:copy-of select="@FundName" /> 
     <xsl:attribute name="FundValue"><xsl:value-of select="format-number(sum(key('Investments', concat(../@Type, '|', ../@InvestmentStrategyId, '|', @FundName))/@FundValue), '0.00')" /></xsl:attribute> 
     </xsl:copy> 
    </xsl:template> 

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

当适用于您的示例XML(与投资的根元素),下面是输出:

<InvestmentAccount Id="Element01_Source3_Sequqence002" Type="Standard" InvestmentStrategyId="Employer" ParameterOverrideIds="AllocationRateOverride"> 
    <Investment FundName="Fund032" FundValue="4754.82" /> 
    <Investment FundName="Fund034" FundValue="4643.48" /> 
    <Investment FundName="Fund035" FundValue="2509.46" /> 
    <Investment FundName="Fund038" FundValue="7104.71" /> 
    <Investment FundName="Fund042" FundValue="4244.08" /> 
</InvestmentAccount> 
    <InvestmentAccount Id="Element01_Source4_Sequence003" Type="DWPRebate" InvestmentStrategyId="DSS" ParameterOverrideIds="DWPAllocationRateOverride"> 
    <Investment FundName="Fund032" FundValue="1881.76" /> 
    <Investment FundName="Fund034" FundValue="1584.18" /> 
    <Investment FundName="Fund035" FundValue="872.99" /> 
    <Investment FundName="Fund038" FundValue="2899.53" /> 
    <Investment FundName="Fund042" FundValue="1762.62" /> 
</InvestmentAccount> 
    <InvestmentAccount Id="Element01_Source2_Sequence001" Type="Standard" InvestmentStrategyId="Employee" ParameterOverrideIds="AllocationRateOverride"> 
    <Investment FundName="Fund032" FundValue="7395.91" /> 
    <Investment FundName="Fund034" FundValue="7222.72" /> 
    <Investment FundName="Fund035" FundValue="3903.52" /> 
    <Investment FundName="Fund038" FundValue="11051.32" /> 
    <Investment FundName="Fund042" FundValue="6602.54" /> 
</InvestmentAccount> 
<InvestmentAccount Id="Element02_Source2_Sequence004" Type="TransferNonPR" InvestmentStrategyId="Employee" ParameterOverrideIds="AllocationRateOverride"> 
    <Investment FundName="Fund032" FundValue="11056.71" /> 
    <Investment FundName="Fund034" FundValue="12401.34" /> 
    <Investment FundName="Fund035" FundValue="6634.86" /> 
    <Investment FundName="Fund038" FundValue="16545.00" /> 
    <Investment FundName="Fund042" FundValue="10036.26" /> 
    <Investment FundName="fictiousextra" FundValue="1414.00" /> 
</InvestmentAccount> 

我不知道你怎么想的分组InvestmentAccount属性元素,但希望你可以自己调整。