Some tuning:
authorberghofe
Wed, 29 Jan 2003 17:35:11 +0100
changeset 13795 cfa3441c5238
parent 13794 332eb2e69a65
child 13796 19f50fa807ae
Some tuning: - finite now uses rev_append (tail recursive!) to append stopper, because @ needs to much stack space for large strings - repeat is now tail recursive
src/Pure/General/scan.ML
--- a/src/Pure/General/scan.ML	Wed Jan 29 17:32:19 2003 +0100
+++ b/src/Pure/General/scan.ML	Wed Jan 29 17:35:11 2003 +0100
@@ -124,7 +124,11 @@
 fun optional scan def = scan || succeed def;
 fun option scan = optional (scan >> Some) None;
 
-fun repeat scan xs = (scan -- repeat scan >> op :: || succeed []) xs;
+fun repeat scan =
+  let fun rep ys xs = (case (Some (scan xs) handle FAIL _ => None) of
+    None => (rev ys, xs) | Some (y, xs') => rep (y :: ys) xs')
+  in rep [] end;
+
 fun repeat1 scan = scan -- repeat scan >> op ::;
 
 fun max leq scan1 scan2 xs =
@@ -184,7 +188,7 @@
   in
     if exists is_stopper input then
       raise ABORT "Stopper may not occur in input of finite scan!"
-    else (force scan --| lift stop) (state, input @ [stopper])
+    else (force scan --| lift stop) (state, rev_append (rev input) [stopper])
   end;
 
 fun finite stopper scan xs =