Reputation: 2141
Say I have an XML document like this:
<library xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="library.xsd"> <book> <title>Harry Potter Sorcerer's Stone</title> <artist>J.K. Rowling</artist> </book> <book> <title>Harry Potter Chamber of Secrets</title> <artist>J.K. Rowling</artist> </book> <book> <title>Harry Potter Prisoner of Azkaban</title> <artist>J.K. Rowling</artist> </book> </library>
I want my XSLT document to find the 3 most commonly used words amongst the titles, and their counts. (So I want to output: "Harry": 3, "Potter": 3, "of": 2).
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:template match="/">
<h2>3 Most Commonly Used Words</h2>
<ul>
<li>Word - Count</li>
</ul>
</xsl:template>
</xsl:stylesheet>
I'm an XML beginner and unclear how to do aggregation using XSLT and XPath. I was thinking some combination of tokenize() and sum()? Can someone point me in the right direction?
Upvotes: 0
Views: 186
Reputation: 66781
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform" version="2.0">
<xsl:output indent="yes"/>
<xsl:template match="/">
<h2>3 Most Commonly Used Words</h2>
<ul>
<xsl:for-each-group group-by="." select="
for $w in //title/tokenize(., '\W+') return $w">
<xsl:sort select="count(current-group())" order="descending" />
<xsl:if test="position() lt 4">
<li>
<xsl:value-of select="current-grouping-key()"/>
<xsl:text> - </xsl:text>
<xsl:value-of select="count(current-group())"/>
</li>
</xsl:if>
</xsl:for-each-group>
</ul>
</xsl:template>
</xsl:stylesheet>
Upvotes: 2