diff options
-rw-r--r-- | lib/js/urweb.js | 39 |
1 files changed, 35 insertions, 4 deletions
diff --git a/lib/js/urweb.js b/lib/js/urweb.js index 93822b17..a952c049 100644 --- a/lib/js/urweb.js +++ b/lib/js/urweb.js @@ -3,8 +3,18 @@ function cons(v, ls) { return { next : ls, data : v }; } +function rev(ls) { + var acc = null; + for (; ls; ls = ls.next) + acc = cons(ls.data, acc); + return acc; +} function concat(ls1, ls2) { - return (ls1 ? cons(ls1.data, concat(ls1.next, ls2)) : ls2); + var acc = ls2; + ls1 = rev(ls1); + for (; ls1; ls1 = ls1.next) + acc = cons(ls1.data, acc); + return acc; } function member(x, ls) { for (; ls; ls = ls.next) @@ -13,13 +23,32 @@ function member(x, ls) { return false; } function remove(x, ls) { - return (ls ? (ls.data == x ? ls.next : cons(ls.data, remove(x, ls.next))) : null); + var acc = null; + + for (; ls; ls = ls.next) + if (ls.data == x) + return concat(acc, ls.next); + else + acc = cons(ls.data, acc); + + return ls; } function union(ls1, ls2) { - return (ls1 ? (member(ls1.data, ls2) ? union(ls1.next, ls2) : cons(ls1.data, union(ls1.next, ls2))) : ls2); + var acc = ls2; + + for (; ls1; ls1 = ls1.next) + if (!member(ls1.data, ls2)) + acc = cons(ls1.data, acc); + + return acc; } function length(ls) { - return (ls ? 1 + length(ls.next) : 0); + var acc = 0; + + for (; ls; ls = ls.next) + ++acc; + + return acc; } @@ -63,6 +92,8 @@ function onFail(f) { function doExn(v) { if (v == null || v.uw_error == null) { var s = (v == null ? "null" : v.toString()); + if (v != null && v.fileName && v.lineNumber) + s += " (" + v.fileName + ":" + v.lineNumber + ")"; runHandlers("Fail", failHandlers, s); } } |