Reputation: 57
Note that some id's repeat and I only want the sum of the count of each unique id. The correct total will be 11.
Note: I had to edit the id on the first set to be 1
Sample Input File:
<?xml version="1.0" encoding="UTF-8"?>
<file>
<item>
<id>1</id>
<count>4</count>
</item>
<item>
<id>2</id>
<count>7</count>
</item>
<item>
<id>2</id>
<count>7</count>
</item>
<item>
<id>2</id>
<count>7</count>
</item>
</file>
Sample Ouput File:
<?xml version="1.0" encoding="UTF-8"?>
<output>
<totalUniqueItemCount>11</totalUniqueItemCount>
</output>
XSLT Attempt:
Here you can see am trying to use for-each group but it is not working for me. I need to be able to get a sum of these counts but I can't figure out how to surround the output of the for-each-group to be able to sum the counts.
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:xs="http://www.w3.org/2001/XMLSchema">
<xsl:output indent="yes" method="xml"/>
<xsl:template match="/file">
<output>
<totalUniqueItemCount>
<xsl:for-each-group select="item" group-by="id">
<xsl:value-of select="xs:integer(count)"/>
</xsl:for-each-group>
</totalUniqueItemCount>
</output>
</xsl:template>
</xsl:stylesheet>
I also tried this approach with no luck:
<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:xs="http://www.w3.org/2001/XMLSchema">
<xsl:output indent="yes" method="xml"/>
<xsl:template match="/file">
<output>
<totalUniqueItemCount>
<xsl:value-of select="sum(item[id ne following-sibling::id]/count)"/>
</totalUniqueItemCount>
</output>
</xsl:template>
</xsl:stylesheet>
Upvotes: 2
Views: 832
Reputation: 117102
how to surround the output of the for-each-group to be able to sum the counts.
You could have done:
<xsl:template match="/file">
<xsl:variable name="unique-counts">
<xsl:for-each-group select="item" group-by="id">
<xsl:copy-of select="count"/>
</xsl:for-each-group>
</xsl:variable>
<output>
<totalUniqueItemCount>
<xsl:value-of select="sum($unique-counts/count)"/>
</totalUniqueItemCount>
</output>
</xsl:template>
But the method suggested by MartinM might be preferable for this scenario.
Upvotes: 0
Reputation: 3445
Just minor change in your second code
use
<xsl:value-of select="sum(item[not(id = following-sibling::item/id)]/count)"/>
instead of
<xsl:value-of select="sum(item[id ne following-sibling::id]/count)"/>
Upvotes: -1
Reputation: 67
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="2.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:xs="http://www.w3.org/2001/XMLSchema">
<xsl:output indent="yes" method="xml"/>
<xsl:key name="itemById" match="file/item" use="id"/>
<xsl:template match="/file">
<output>
<totalUniqueItemCount>
<xsl:value-of select="sum(//item[generate-id(.) = generate-id(key('itemById',id)[1])]/count)"/>
</totalUniqueItemCount>
</output>
</xsl:template>
</xsl:stylesheet>
https://xsltfiddle.liberty-development.net/3Mvnt44/1
Upvotes: 1