I slightly modified the original transformation to get the desired result. Basically, the apply template rule is a solution that solves the parentesis function. To determine whether to insert or not to insert a comma, I check the following sibling elements of different types.
In addition, I replaced your xsl:sequence with xsl:value-of , thereby preventing the creation of unwanted spaces (I am impressed that they are undesirable). The element() function has also been replaced. The style sheet is now compatible with XSLT 1.0. I don't like XSLT 1.0, but I prefer to use new features only when it's really needed.
This solution is not very general (MATHML is a huge specification that you know), but you can use it and adapt it to more complex cases.
XSLT 1.0 is being tested in Saxon 6.5.5
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> <xsl:output method="text" encoding="UTF-8"/> <xsl:strip-space elements="*"/> <xsl:template match="apply"> <xsl:value-of select="concat(name(child::*[1]),'(')"/> <xsl:apply-templates select="apply|cn|ci"/> <xsl:value-of select="')'"/> <xsl:if test="count(following-sibling::*)"> <xsl:value-of select="','"/> </xsl:if> </xsl:template> <xsl:template match="cn|ci"> <xsl:value-of select="."/> <xsl:if test="count(following-sibling::*)>0"> <xsl:value-of select="','"/> </xsl:if> </xsl:template> </xsl:stylesheet>
When applied to the input shown in the question, the following occurs:
eq(plus(power(x,2),times(2,x),2),0)
source share