fix(CCVector): always obtain a copy of array before using unsafe_{set,get}

close #423
This commit is contained in:
Simon Cruanes 2023-01-06 16:31:36 -05:00
parent b0ed8d9182
commit b73fc4ee5c

View file

@ -333,34 +333,40 @@ let uniq_sort cmp v =
(* start at 1, to get the first element in hand *) (* start at 1, to get the first element in hand *)
let iter k v = let iter k v =
let n = v.size in let { vec; size = n } = v in
for i = 0 to n - 1 do for i = 0 to n - 1 do
k (Array.unsafe_get v.vec i) k (Array.unsafe_get vec i)
done done
let iteri k v = let iteri k v =
let n = v.size in let { vec; size = n } = v in
for i = 0 to n - 1 do for i = 0 to n - 1 do
k i (Array.unsafe_get v.vec i) k i (Array.unsafe_get vec i)
done done
let map f v = let map f v =
if array_is_empty_ v then if array_is_empty_ v then
create () create ()
else ( else (
let vec = Array.init v.size (fun i -> f (Array.unsafe_get v.vec i)) in let { vec; size } = v in
{ size = v.size; vec } let vec = Array.init size (fun i -> f (Array.unsafe_get vec i)) in
{ size; vec }
) )
let mapi f v = let mapi f v =
if array_is_empty_ v then if array_is_empty_ v then
create () create ()
else ( else (
let vec = Array.init v.size (fun i -> f i (Array.unsafe_get v.vec i)) in let { vec; size } = v in
{ size = v.size; vec } let vec = Array.init size (fun i -> f i (Array.unsafe_get vec i)) in
{ size; vec }
) )
let map_in_place f v = iteri (fun i x -> Array.unsafe_set v.vec i (f x)) v let map_in_place f v =
let { vec; size = n } = v in
for i = 0 to n - 1 do
Array.unsafe_set vec i (f (Array.unsafe_get vec i))
done
let filter_in_place p v = let filter_in_place p v =
let i = ref 0 in let i = ref 0 in
@ -392,11 +398,12 @@ let filter p v =
) )
let fold f acc v = let fold f acc v =
let { vec; size } = v in
let rec fold acc i = let rec fold acc i =
if i = v.size then if i = size then
acc acc
else ( else (
let x = Array.unsafe_get v.vec i in let x = Array.unsafe_get vec i in
fold (f acc x) (i + 1) fold (f acc x) (i + 1)
) )
in in
@ -545,9 +552,9 @@ let rev v =
v' v'
let rev_iter f v = let rev_iter f v =
let n = v.size in let { vec; size = n } = v in
for i = n - 1 downto 0 do for i = n - 1 downto 0 do
f (Array.unsafe_get v.vec i) f (Array.unsafe_get vec i)
done done
let size v = v.size let size v = v.size
@ -566,9 +573,9 @@ let of_seq ?(init = create ()) seq =
let to_iter v k = iter k v let to_iter v k = iter k v
let to_iter_rev v k = let to_iter_rev v k =
let n = v.size in let { vec; size = n } = v in
for i = n - 1 downto 0 do for i = n - 1 downto 0 do
k (Array.unsafe_get v.vec i) k (Array.unsafe_get vec i)
done done
let to_seq v = let to_seq v =
@ -592,9 +599,10 @@ let to_seq_rev v =
let slice_iter v start len = let slice_iter v start len =
assert (start >= 0 && len >= 0); assert (start >= 0 && len >= 0);
fun k -> fun k ->
assert (start + len <= v.size); let { size; vec } = v in
assert (start + len <= size);
for i = start to start + len - 1 do for i = start to start + len - 1 do
let x = Array.unsafe_get v.vec i in let x = Array.unsafe_get vec i in
k x k x
done done