How to write a while loop in MarkLogic XQuery
marklogic, xquery
Solution
Recursion is the usual way. Another is to use a FLWOR with a `try-catch` and throw an exception with a known code to exit early.
try {
for $x in 1 to count($tokens)
return tok($x) }
catch ($ex) {
if ($x/error:code eq 'BREAK') then ()
else xdmp:rethrow() }
The `tok` function would call `error((), 'BREAK')` to exit the parent FLWOR expression. If needed you could multiply the token count by some factor, or use an arbitrary large number.
https://github.com/robwhitby/xray/blob/coverage/src/coverage.xqy has a more complex example, in the `cover:actual-via-debug` function.
Problem
Is there any recognized idiom for writing the equivalent of a while loop in MarkLogic XQuery? I know that I could write a tail-recursive routine, but MarkLogic XQuery does not optimize tail-recursion and I'm getting a stack overflow (I have to go around my loop ~20000 times). Editorial note: as of MarkLogic 6, tail recursion is optimized in MarkLogic.