Возвращая значение из оператора do в haskell охранника
Я пытаюсь найти, если какая-то буква уже используется в любой строке в списке строк. Если да - выберите следующую букву для сравнения. Если нет - верните это письмо и обновите первоначальный список.
Для проверки в списке я использую:
check:: [String] -> Char -> Char
check s c
| any (elem c) s = check s (next c)
| otherwise = do update s c
return c
Но это дает мне ошибку:
Не удалось сопоставить тип "[Char]" с "Char"
Ожидаемый тип: [String] -> [Char] -> Char
Фактический тип: [String] -> [Char] -> [Char]
В блоке 'do' блока: update sc
Моя функция обновления имеет следующую декларацию:
update:: [String] -> Char -> [String]
Есть ли правильный способ выполнить 2 действия в охране? otherwise
? Мне нужно вернуть c, чтобы использовать его в другой рекурсивной функции, которая принимает в качестве параметров как Char
с и обновил [String]
s
Когда у меня были эти функции, возвращающие только c, без обновления списка, там, где нет ошибок:
check:: [String] -> Char -> Char
check s c
| any (elem c) s = check s (next c)
| otherwise = c
Любые советы приветствуются.
Обновление: моя следующая функция:
next :: Char -> Char
next 'Z' = 'A'
next c = chr (ord c + 1)
И для обновления я попробовал:
update:: [String] -> Char -> [String]
update s c = s ++ [[c]]
Дело в том, что позже мне нужно использовать [String]
который является результатом обновления, вместе с Char
c (результат проверки) в другую функцию. Поэтому после выполнения проверки мне нужно вернуть значение и обновить список с ним.
1 ответ
Haskell - это функциональный язык, поэтому вы не можете (не должны) думать о мутировании структуры данных, вместо этого функция должна возвращать обновленную версию этой структуры данных и все остальное, что вам нужно. Самый распространенный способ сделать это - вернуть набор нужных вам значений. Вот что вы, вероятно, ищете:
check:: [String] -> Char -> (Char, [String])
check s c
| any (elem c) s = check s (next c)
| otherwise = (c, s ++ [[c]])
Таким образом, вы получите "это" письмо и обновленную версию первоначального списка String
s.