Ошибка идентификатора несвязанного значения SML в функции вставки
У меня проблема с моей отдельной функцией. Separate возвращает список, который вставляет элемент x после каждого k элементов списка l (считая от конца списка). Например, отдельный (1, 0, [1,2,3,4]) должен возвращать [1,0,2,0,3,0,4] и отдельный (3, 0, [1,2,3,4]) должен вернуть [1,0,2,3,4]. Всякий раз, когда я запускаю какие-либо тесты на нем, я получаю ошибку:
! Unbound value identifier: separate
Это код, который я использую:
(*Function returns length of lst *)
fun length(lst: int list): int =
case lst of
[] => 0
| h::t => 1 + length(t)
(*Insert element x at the kth position in the list
and return the new list*)
fun kinsert [] x k = [x]
| kinsert ls x 0 = x::ls
| kinsert (l::ls) x k = l::(kinsert ls x (k - 1))
(* c: keeps track of where we are in the list
n: determines if we insert element at given position
z: holds length of the list *)
fun sep_help k x l c n z=
if c = z then l
else if n = k then (sep_help k x (kinsert l x c) (c+2) 0 z )
else (sep_help k x l (c+2) (n+1) z) ;
(*Returns list l with x inserted after each k element *)
fun separate (k: int, x: 'a, l: 'a list) : 'a list =
| separate k x l = (sep_help k x l 0 0 (length l));
Кто-нибудь знает, что может быть причиной ошибки?
1 ответ
Ваш separate
Похоже, что это объединение двух разных определений - сначала нетипичная версия без определения, а затем каррированная версия с таким определением.
Ты наверное имел ввиду
fun separate (k: int, x: 'a, l: 'a list) : 'a list = sep_help k x l 0 0 (length l);
Но работа в обратном порядке через список несколько усложняет ситуацию.
Намного легче работать с головы до хвоста и переворачивать список до и после обработки.
Тогда "все", что вам нужно, - это помощник, который вставляет элемент в каждое k-ое место списка.
Что-то вроде этого, возможно:
(*Returns list l with x inserted after each k element *)
fun separate (k: int, x: 'a, l: 'a list) : 'a list =
let
fun kinsert [] _ = []
| kinsert ls 0 = x::(kinsert ls k)
| kinsert (l::ls) i = l::(kinsert ls (i-1))
in
List.rev (kinsert (List.rev l) k)
end