Creating Polymorphic XSLT

Problem

You want to create XSLT that performs the same function on disparate data.

Solution

There are two kinds of polymorphic behavior in XSLT. The first form is reminiscent of overloading, and the second is similar to overriding.

Some modern languages, notably C++, let you create overloaded functions: functions that have the same name but take different types as arguments. The compiler figures out which version of the function to call based on the type of data passed to it at the point of call. XSLT does not have this exact capability; however, consider the following stylesheet:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:output method="html" /> <xsl:template match="/"> <html> <head> <title>Area of Shapes</title> </head> <body> <h1>Area of Shapes</h1> <table cellpadding="2" border="1"> <tbody> <tr> <th>Shape</th> <th>Shape Id</th> <th>Area</th> </tr> <xsl:apply-templates/> </tbody> </table> </body> </html> </xsl:template> <xsl:template match="shape"> <tr> <td><xsl:value-of select="@kind"/></td> <td><xsl:value-of select="@id"/></td> <xsl:variable name="area"> <xsl:apply-templates select="." mode="area"/> </xsl:variable> <td align="right"><xsl:value-of select="format-number($area,'#.000')"/></td> </tr> </xsl:template> <xsl:template match="shape[@kind='triangle']" mode="area"> <xsl:value-of select="@base * @height"/> </xsl:template> <xsl:template match="shape[@kind='square']" mode="area"> <xsl:value-of select="@side ...

Get XSLT Cookbook now with the O’Reilly learning platform.

O’Reilly members experience books, live events, courses curated by job role, and more from O’Reilly and nearly 200 top publishers.