Re: [xsl] unfolding compressed equivalents

Subject: Re: [xsl] unfolding compressed equivalents
From: Tony Graham <Tony.Graham@xxxxxxxxxxxxxxxxxxxxxx>
Date: Thu, 24 Jan 2008 22:11:29 +0000
On Wed, Jan 23 2008 20:25:36 +0000, mariebilderas@xxxxxxxxx wrote:
...
> AN EXAMPLE:
> In a Danish-English dictionary, I have this extremely compressed
> English equivalent(s):
> "[last] Sunday (or Monday or Tuesday) evening (or night) I was at home"
>
> - The use of [square brackets] indicate, that the content can be omitted.
> - Alternatives to a word - or to a sequence of words - are shown in
> one (parenthesis), separated by the word "or".
> - Brackets, parenthesis and or's are of course just presentational.
...
> THE GOAL:
> In my online dictionary, I would like to show this same equivalent like this:
...
> The resulting underlying xml should thus look like this:
> <equivalent>last Sunday evening I was at home</equivalent>
> <equivalent>last Sunday night I was at home</equivalent>
> <equivalent>last Monday evening I was at home</equivalent>
> <equivalent>last Monday night I was at home</equivalent>
> <equivalent>last Tuesday evening I was at home</equivalent>
> <equivalent>last Tuesday night I was at home</equivalent>
> <equivalent>Sunday evening I was at home</equivalent>
> <equivalent>Sunday night I was at home</equivalent>
> <equivalent>Monday evening I was at home</equivalent>
> <equivalent>Monday night I was at home</equivalent>
> <equivalent>Tuesday evening I was at home</equivalent>
> <equivalent>Tuesday night I was at home</equivalent>
>
> Can anyone help me through function-calls and recursions? I am using
> XSLT 2.0.

Since you're starting with text, you can use xsl:analyze-string, make
elements corresponding to your notional markup, and then process that
markup to produce your <equivalent> elements.

The stylesheet below borrows from David Carlisle's solution for
processing the markup.

------------------------------------------------------------
<xsl:stylesheet
  version="2.0"
  xmlns:xsl="http://www.w3.org/1999/XSL/Transform";>

  <xsl:output method="xml" indent="yes"/>

  <xsl:variable name="string"
    select="'[last] Sunday (or Monday or Tuesday) evening (or night) I was at home'"/>
  
  <xsl:template match="/">
    <xsl:variable name="equivalents">
      <equivalents>
        <xsl:analyze-string select="$string"
          regex="\[([^\[]+)\]">
          <xsl:matching-substring>
            <omittable><xsl:value-of select="regex-group(1)"/></omittable>
          </xsl:matching-substring>
          <xsl:non-matching-substring>
            <xsl:analyze-string select="."
              regex="(\S+)\s+\(([^(]+)\)">
              <xsl:matching-substring>
                <alternatives>
                  <either><xsl:value-of select="regex-group(1)"/></either>
                  <xsl:analyze-string select="regex-group(2)"
                    regex="or\s+(\S+)\s*">
                    <xsl:matching-substring>
                      <or><xsl:value-of select="regex-group(1)"/></or>
                    </xsl:matching-substring>
                    <xsl:non-matching-substring>
                      <xsl:message>Unexpected text: '<xsl:value-of select="."/>' in '<xsl:value-of select="$string"/>'</xsl:message>
                    </xsl:non-matching-substring>
                  </xsl:analyze-string>
                </alternatives>
              </xsl:matching-substring>
              <xsl:non-matching-substring>
                <xsl:value-of select="."/>
              </xsl:non-matching-substring>
            </xsl:analyze-string>
          </xsl:non-matching-substring>
        </xsl:analyze-string>
        <x/>
      </equivalents>
    </xsl:variable>
    <!--<xsl:copy-of select="$equivalents"/>-->
    <equivalents>
      <xsl:apply-templates select="$equivalents/equivalents/node()[1]"/>
    </equivalents>
  </xsl:template>

  <xsl:template match="equivalents/text()">
    <xsl:param name="done" as="node()*"/>
    <xsl:apply-templates select="following-sibling::*[1]">
      <xsl:with-param name="done" select="$done, ."/>
    </xsl:apply-templates>
  </xsl:template>

  <xsl:template match="omittable">
    <xsl:param name="done" as="node()*"/>
    <xsl:apply-templates select="following-sibling::node()[1]">
      <xsl:with-param name="done" select="$done"/>
    </xsl:apply-templates>
    <xsl:apply-templates select="following-sibling::node()[1]">
      <xsl:with-param name="done" select="$done, ."/>
    </xsl:apply-templates>
  </xsl:template>

  <xsl:template match="alternatives">
    <xsl:param name="done" as="node()*"/>
    <xsl:variable name="following" select="following-sibling::node()[1]"/>
    <xsl:for-each select="*">
      <xsl:apply-templates select="$following">
        <xsl:with-param name="done" select="$done, ."/>
      </xsl:apply-templates>
    </xsl:for-each>
  </xsl:template>

  <xsl:template match="x">
    <xsl:param name="done" as="node()*"/>
 :<equivalent><xsl:value-of select="$done" separator=""/></equivalent>
  </xsl:template>

</xsl:stylesheet>
------------------------------------------------------------

Regards,


Tony Graham.
======================================================================
Tony.Graham@xxxxxxxxxxxxxxxxxxxxxx   http://www.menteithconsulting.com

Menteith Consulting Ltd             Registered in Ireland - No. 428599
Registered Office: 13 Kelly's Bay Beach, Skerries, Co. Dublin, Ireland
----------------------------------------------------------------------
Menteith Consulting -- Understanding how markup works
======================================================================

Current Thread