[MarkLogic Dev General] Re: Recursive descent: typeswitch v.
XSL's apply-templates (& xsl:template/@match)
Robert Koberg
rob at koberg.com
Thu Aug 28 12:44:29 PDT 2008
OK. That is what I expected. I don't know if I would say that is more
maintainable.
Another benefit of using XSL in situations like this is 'overloading.'
Say I have several projects that transform ComplexSchema to XHTML.
Each project is basically the same with minor differences. I would
have a general purpose set of templates that I xsl:import into a
primary XSL for each project. There I can override templates as needed
while keeping the general purpose set the same. Doing the same with
XQuery would be cumbersome at best.
In other words, in XSL, it is generally better to always apply-
templates (even if it is on the current context node) rather than call
functions or templates. This definitely increases reusability and
greatly helps future maintenance. Am I missing a way to do this in
XQuery?
best,
-Rob
On Aug 28, 2008, at 3:20 PM, David Sewell wrote:
> On Thu, 28 Aug 2008, Robert Koberg wrote:
>
>> Interesting and well said.
>>
>> I don't suppose your XQuery is something that can be shared publicly?
>
> No, but below in a nutshell is the basic strategy. There are two basic
> functions: rend:main(), which would be called on the outermost node
> you
> need to process (it could be a document node, a root element,
> whatever),
> containing all the typeswitches; and rend:recurse(), that is mostly
> just
> a way to let you say
>
> <p>{rend:recurse($node)}</p>
>
> rather than
>
> <p>{for $n in $node/node() return rend:main($n)}</p>
>
> within the typeswitch.
>
> For simple cases, you can put the transform right in the typeswitch.
> For
> other cases, each typeswitch calls a custom function that is more or
> less equivalent to an XSLT template matching the element. Logic can be
> put within the typeswitch statement or pushed off onto the custom
> functions as suits you.
>
> =====
> define function rend:main(
> $content as node()*
> ) as node()* {
> for $node in $content-new/node()
> return typeswitch($node)
> case element(simple) return <newName>{rend:recurse($node)}</
> newName>
> case element(complex) return rend:complex($node)
> case element(moreComplex) return
> if ($something) then rend:moreComplex1($node)
> else rend:moreComplex2($node)
> default return rend:default($node)
> }
>
> define function rend:recurse(
> (: just recurses back to rend:main() :)
> $node as node()
> ) as node()* {
> (: live code actually does various stuff here before
> it recurses :)
> rend:main($node)
> }
>
> define function rend:complex(
> (: example of 'template' function :)
> $el as element()
> ) as element() {
> element complex {
> attribute xml:id { $el:id }
> attribute class { $el/@type }
> rend:recurse($el)
> }
> }
>
> (: etc. :)
>
> --
> David Sewell, Editorial and Technical Manager
> ROTUNDA, The University of Virginia Press
> PO Box 801079, Charlottesville, VA 22904-4318 USA
> Courier: 310 Old Ivy Way, Suite 302, Charlottesville VA 22903
> Email: dsewell at virginia.edu Tel: +1 434 924 9973
> Web: http://rotunda.upress.virginia.edu/
> _______________________________________________
> General mailing list
> General at developer.marklogic.com
> http://xqzone.com/mailman/listinfo/general
More information about the General
mailing list