 |
| XSLT General questions and answers about XSLT. For issues strictly specific to the book XSLT 1.1 Programmers Reference, please post to that forum instead. |
Welcome to the p2p.wrox.com Forums.
You are currently viewing the XSLT section of the Wrox Programmer to Programmer discussions. This is a community of software programmers and website developers including Wrox book authors and readers. New member registration was closed in 2019. New posts were shut off and the site was archived into this static format as of October 1, 2020. If you require technical support for a Wrox book please contact http://hub.wiley.com
|
|
|
|

June 27th, 2012, 12:27 PM
|
|
Registered User
|
|
Join Date: Jun 2012
Posts: 20
Thanks: 12
Thanked 0 Times in 0 Posts
|
|
Summing attribute values in a HTML Table
Hello All,
I am creating a HTML page using XSLT from XML and I would like to add a summary row at the bottom of the output. My XML looks like this:
Code:
<data>
<items>
<item id="1" attr_1="123" attr_2="112" attr_3="22"/>
<item id="2" attr_1="12" attr_2="112" attr_3="38"/>
<item ... />
</items>
</data>
I can get easily get my HTML to resemble my XML for the item elements but no matter what I try I can't get a sum(attr_1) to work. I either get the value from the first <item> or errors regarding strings amongst others or just no output.
I assume it can be done, but evidently not by me, can anyone help me out here please, so in an ideal world my HTML would like this:
Code:
1 123 112 22
2 12 112 38
...
Summary 243 224 60
--
Bill
|
|

June 27th, 2012, 01:11 PM
|
 |
Wrox Author
|
|
Join Date: Apr 2004
Posts: 4,962
Thanks: 0
Thanked 292 Times in 287 Posts
|
|
It's easier to answer this question if you show us your best attempt at a solution: then we can see where you went wrong and explain the concept that you failed to understand. Sometimes it's context, sometimes it's namespaces, sometimes it's as simple as forgetting the "@" sign - it's much more educational to tell you where your mistake is than to give you a correct solution.
If the context is the items element then this is as simple as calling sum(item/@attr_1)
__________________
Michael Kay
http://www.saxonica.com/
Author, XSLT 2.0 and XPath 2.0 Programmer\'s Reference
|
|

June 27th, 2012, 01:53 PM
|
|
Registered User
|
|
Join Date: Jun 2012
Posts: 20
Thanks: 12
Thanked 0 Times in 0 Posts
|
|
Quote:
Originally Posted by mhkay
It's easier to answer this question if you show us your best attempt at a solution: then we can see where you went wrong and explain the concept that you failed to understand. Sometimes it's context, sometimes it's namespaces, sometimes it's as simple as forgetting the "@" sign - it's much more educational to tell you where your mistake is than to give you a correct solution.
If the context is the items element then this is as simple as calling sum(item/@attr_1)
|
Hi, thank you for the reply and your time, very much appreciated. This gives me only the first item value and not a sum of the whole column as I'd hoped.
Code:
<xsl:template name="summaries">
<xsl:for-each select="./item/@*">
<xsl:if test="name() != 'id'">
<td width="120"><xsl:value-of select="sum(.)"/></td>
</xsl:if>
</xsl:for-each>
</xsl:template>
This is called from another template that matches /data/items/
--
Bill
|
|

June 27th, 2012, 05:29 PM
|
 |
Wrox Author
|
|
Join Date: Apr 2004
Posts: 4,962
Thanks: 0
Thanked 292 Times in 287 Posts
|
|
"." always refers to a single item and the sum of a single item is the value of that item.
There's another problem in your code, which is that you are assuming the order of attributes is predictable, which is not the case.
Try something like this:
Code:
<xsl:template name="summaries">
<xsl:variable name="items" select="."/>
<xsl:for-each select="item[1]/@*[name() != 'id']">
<xsl:sort select="name()"/>
<td width="120"><xsl:value-of select="sum($items/item/@*[name() = name(current())]"/></td>
</xsl:if>
</xsl:for-each>
</xsl:template>
__________________
Michael Kay
http://www.saxonica.com/
Author, XSLT 2.0 and XPath 2.0 Programmer\'s Reference
|
|
The Following User Says Thank You to mhkay For This Useful Post:
|
|
|

June 28th, 2012, 04:45 AM
|
|
Registered User
|
|
Join Date: Jun 2012
Posts: 20
Thanks: 12
Thanked 0 Times in 0 Posts
|
|
Quote:
Originally Posted by mhkay
"." always refers to a single item and the sum of a single item is the value of that item.
|
I am aware of this which is why I was using the for-each, and also showing my lack of knowledge on the subject!
Quote:
Originally Posted by mhkay
There's another problem in your code, which is that you are assuming the order of attributes is predictable, which is not the case.
Try something like this:
Code:
<xsl:template name="summaries">
<xsl:variable name="items" select="."/>
<xsl:for-each select="item[1]/@*[name() != 'id']">
<xsl:sort select="name()"/>
<td width="120"><xsl:value-of select="sum($items/item/@*[name() = name(current())]"/></td>
</xsl:if>
</xsl:for-each>
</xsl:template>
|
After adding the missing ) on the sum and removing the </xsl:if> this work for me thank you very much, it would have taken me a long time to get there. But maybe you could explain why when it sums a column of 0 (zeros) it returns nothing! Should you not at least get 0 back out?
--
Bill
|
|

June 28th, 2012, 05:50 AM
|
 |
Wrox Author
|
|
Join Date: Apr 2004
Posts: 4,962
Thanks: 0
Thanked 292 Times in 287 Posts
|
|
>But maybe you could explain why when it sums a column of 0 (zeros) it returns nothing! Should you not at least get 0 back out?
No, I can't. The sum of a set of zero values is zero.
__________________
Michael Kay
http://www.saxonica.com/
Author, XSLT 2.0 and XPath 2.0 Programmer\'s Reference
|
|

June 28th, 2012, 06:22 AM
|
|
Registered User
|
|
Join Date: Jun 2012
Posts: 20
Thanks: 12
Thanked 0 Times in 0 Posts
|
|
Quote:
Originally Posted by mhkay
>But maybe you could explain why when it sums a column of 0 (zeros) it returns nothing! Should you not at least get 0 back out?
No, I can't. The sum of a set of zero values is zero.
|
No, but I can! I neglected to mention that I'd wrapped the output in a format-number(...) function and that I was using # instead of 0! So my apologies for that.
|
|
 |