mirror of
https://github.com/c-cube/ocaml-containers.git
synced 2025-12-06 03:05:28 -05:00
fix(vector): free elements in more functions, add fill_empty_slots_with
see #235
This commit is contained in:
parent
ff58dc0b5f
commit
3b0ceb7821
2 changed files with 47 additions and 1 deletions
|
|
@ -511,7 +511,6 @@ let map_in_place f v =
|
|||
*)
|
||||
|
||||
|
||||
(* TODO: free elements *)
|
||||
let filter' p v =
|
||||
let i = ref 0 in (* cur element *)
|
||||
let j = ref 0 in (* cur insertion point *)
|
||||
|
|
@ -525,6 +524,10 @@ let filter' p v =
|
|||
incr j
|
||||
) else incr i
|
||||
done;
|
||||
(* free elements *)
|
||||
if !j > 0 && !j < v.size then (
|
||||
Array.fill v.vec !j (v.size - !j) v.vec.(0);
|
||||
);
|
||||
v.size <- !j
|
||||
|
||||
(*$T
|
||||
|
|
@ -682,6 +685,10 @@ let filter_map_in_place f v =
|
|||
incr i;
|
||||
incr j
|
||||
done;
|
||||
(* free elements *)
|
||||
if !j > 0 && !j < v.size then (
|
||||
Array.fill v.vec !j (v.size - !j) v.vec.(0);
|
||||
);
|
||||
v.size <- !j
|
||||
|
||||
(*$QR
|
||||
|
|
@ -691,6 +698,19 @@ let filter_map_in_place f v =
|
|||
to_list v = CCList.filter_map f l)
|
||||
*)
|
||||
|
||||
(* check it frees memory properly *)
|
||||
(*$R
|
||||
let s = "coucou" ^ "lol" in
|
||||
let w = Weak.create 1 in
|
||||
Weak.set w 0 (Some s);
|
||||
let v = of_list ["a"; s] in
|
||||
filter' (fun s -> String.length s <= 1) v;
|
||||
assert_equal 1 (length v);
|
||||
assert_equal "a" (get v 0);
|
||||
Gc.major();
|
||||
assert_equal None (Weak.get w 0);
|
||||
*)
|
||||
|
||||
let flat_map f v =
|
||||
let v' = create () in
|
||||
iter (fun x -> iter (push v') (f x)) v;
|
||||
|
|
@ -817,6 +837,25 @@ let slice_seq v start len =
|
|||
|
||||
let slice v = (v.vec, 0, v.size)
|
||||
|
||||
let fill_empty_slots_with v x : unit =
|
||||
if capacity v > length v then (
|
||||
Array.fill v.vec (length v) (capacity v - length v) x;
|
||||
)
|
||||
|
||||
(* check it frees memory properly *)
|
||||
(*$R
|
||||
let s = "coucou" ^ "lol" in
|
||||
let w = Weak.create 1 in
|
||||
Weak.set w 0 (Some s);
|
||||
let v = of_list ["a"; s] in
|
||||
ignore (pop_exn v :string);
|
||||
assert_equal ~printer:string_of_int 1 (length v);
|
||||
assert_equal ~printer:CCFun.id "a" (get v 0);
|
||||
fill_empty_slots_with v "";
|
||||
Gc.major();
|
||||
assert_equal None (Weak.get w 0);
|
||||
*)
|
||||
|
||||
let (--) i j =
|
||||
if i>j
|
||||
then init (i-j+1) (fun k -> i-k)
|
||||
|
|
|
|||
|
|
@ -275,6 +275,13 @@ val slice_seq : ('a,_) t -> int -> int -> 'a sequence
|
|||
(** [slice_seq v start len] is the sequence of elements from [v.(start)]
|
||||
to [v.(start+len-1)]. *)
|
||||
|
||||
val fill_empty_slots_with : ('a, _) t -> 'a -> unit
|
||||
(** [fill_empty_slots_with v x] puts [x] in the slots of [v]'s underlying
|
||||
array that are not used (ie in the last [capacity v - length v] slots).
|
||||
This is useful if you removed some elements from the vector and
|
||||
want to be sure they can be GC'd by erasing them from the vector.
|
||||
@since NEXT_RELEASE *)
|
||||
|
||||
val of_klist : ?init:('a, rw) t -> 'a klist -> ('a, rw) t
|
||||
val to_klist : ('a,_) t -> 'a klist
|
||||
val of_gen : ?init:('a, rw) t -> 'a gen -> ('a, rw) t
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue