我正在尝试在OCaml中创建一个函数,它可以提供" k-average"列表中的连续元素。例如:
average 4 [1; 2; 3; 4; 5; 6] = [2; 3; 4]
由于1,2,3,4的平均值为2,因此2,3,4,5的平均值为3,3,4,5,6的平均值为4.
我创建了一个平均列表的函数,但是每两个元素都有一个:
let rec average2 xs = match xs with
| [] -> []
| x :: [] -> [x]
| x :: x' :: xs -> if xs = [] then [(x + x') / 2] else [(x + x') / 2] @
(average2 (x'::xs))
如何修改它以允许我平均k元素?
答案 0 :(得分:1)
你应该做的只是验证列表是否具有适当的长度,然后两个递归函数将轻松完成:
let average n l =
if List.length l < n then failwith "List is too small"
else
(* this function computes one k-average and returns the result *)
let rec aux2 acc i = function
| hd :: tl when i < n -> aux2 (acc + hd) (i + 1) tl
| _ -> acc / n
in
let rec aux acc l = match l with
(* the resulting list is reversed *)
| [] -> List.rev acc
| _ :: tl ->
(* Get the k-average of the k first elements of the list *)
let avgn = aux2 0 0 l in
(* if the rest of the list is too small, we reached the
end for sure, end *)
if List.length tl < n then List.rev (avgn :: acc)
(* recursive call on the rest of the list (without the head) *)
else aux (avgn :: acc) tl
in aux [] l