bugfix: using the same ExitSequence exception in take and is_empty cannot work

This commit is contained in:
Simon Cruanes 2014-10-19 20:51:04 +02:00
parent a193c54081
commit 9fc9a311e4

View file

@ -319,33 +319,37 @@ let min ?(lt=fun x y -> x < y) seq =
| Some y -> if lt x y then ret := Some x); | Some y -> if lt x y then ret := Some x);
!ret !ret
exception ExitSequence exception ExitHead
let head seq = let head seq =
let r = ref None in let r = ref None in
try try
seq (fun x -> r := Some x; raise ExitSequence); None seq (fun x -> r := Some x; raise ExitHead); None
with ExitSequence -> !r with ExitHead -> !r
let head_exn seq = let head_exn seq =
match head seq with match head seq with
| None -> invalid_arg "Sequence.head_exn" | None -> invalid_arg "Sequence.head_exn"
| Some x -> x | Some x -> x
exception ExitTake
let take n seq k = let take n seq k =
let count = ref 0 in let count = ref 0 in
try try
seq (fun x -> seq (fun x ->
if !count = n then raise ExitSequence; if !count = n then raise ExitTake;
incr count; incr count;
k x; k x;
) )
with ExitSequence -> () with ExitTake -> ()
exception ExitTakeWhile
let take_while p seq k = let take_while p seq k =
try try
seq (fun x -> if p x then k x else raise ExitSequence) seq (fun x -> if p x then k x else raise ExitTakeWhile)
with ExitSequence -> () with ExitTakeWhile -> ()
let drop n seq k = let drop n seq k =
let count = ref 0 in let count = ref 0 in
@ -362,29 +366,35 @@ let rev seq =
let l = MList.of_seq seq in let l = MList.of_seq seq in
fun k -> MList.iter_rev k l fun k -> MList.iter_rev k l
exception ExitForall
let for_all p seq = let for_all p seq =
try try
seq (fun x -> if not (p x) then raise ExitSequence); seq (fun x -> if not (p x) then raise ExitForall);
true true
with ExitSequence -> false with ExitForall -> false
exception ExitExists
(** Exists there some element satisfying the predicate? *) (** Exists there some element satisfying the predicate? *)
let exists p seq = let exists p seq =
try try
seq (fun x -> if p x then raise ExitSequence); seq (fun x -> if p x then raise ExitExists);
false false
with ExitSequence -> true with ExitExists -> true
let mem ?(eq=(=)) x seq = exists (eq x) seq let mem ?(eq=(=)) x seq = exists (eq x) seq
exception ExitFind
let find f seq = let find f seq =
let r = ref None in let r = ref None in
begin try begin try
seq (fun x -> match f x with seq (fun x -> match f x with
| None -> () | None -> ()
| Some _ as res -> r := res | Some _ as res -> r := res; raise ExitFind
); );
with ExitSequence -> () with ExitFind -> ()
end; end;
!r !r
@ -393,17 +403,19 @@ let length seq =
seq (fun _ -> incr r); seq (fun _ -> incr r);
!r !r
exception ExitIsEmpty
let is_empty seq = let is_empty seq =
try seq (fun _ -> raise ExitSequence); true try seq (fun _ -> raise ExitIsEmpty); true
with ExitSequence -> false with ExitIsEmpty -> false
(** {2 Transform a sequence} *) (** {2 Transform a sequence} *)
let empty2 k = () let empty2 k = ()
let is_empty2 seq2 = let is_empty2 seq2 =
try ignore (seq2 (fun _ _ -> raise ExitSequence)); true try ignore (seq2 (fun _ _ -> raise ExitIsEmpty)); true
with ExitSequence -> false with ExitIsEmpty -> false
let length2 seq2 = let length2 seq2 =
let r = ref 0 in let r = ref 0 in