Повторения как гиломорфизм

Итак, я пытался преобразовать эту функцию на Haskell, которая проверяет, нет ли в списке повторений, в Hylomorphism, но в этом есть что-то странное.

valid :: [a] -> Bool
valid [] = True
valid (h:t) = if (not (elem h t)) then valid t else False  

Я буду рад, если кто-нибудь может помочь! Спасибо

1 ответ

Хорошо, hylomoprhism - функция h: A → C, которая может быть определена в части анаморфизма (g и p) и катаморфизма (c и ).

Часть анаморфизма состоит из функции g: A → B × A, которая "разворачивает" объект на более мелкие части, и p: A → Bool - предикат, который определяет, закончили ли мы развертывание.

Часть катаморфизма состоит из значения c ∈ C и оператора ⊕: B × C → C.

(этот текст является слегка измененной версией страницы Википедии)

В вашем случае развертывание означает, что мы разворачиваем список с некоторым значением (типа B, и рекурсивной частью, то есть здесь хвост списка).

Предикат p может быть выведен из вашего определения: если список пуст, то мы прекратили. Понятно, что в этом случае мы возвращаемся True, так что это означает, что с True,

Так что же теперь будет за B- часть? Хорошо, если мы посмотрим на вашу функцию, нам нужен доступ как к заголовку, так и к концу списка, поэтому B можно рассматривать как 2-кортеж, содержащий заголовок (как первый элемент) и хвост (как второй элемент).

Итак, теперь остаётся вопрос: что делает? Он принимает в качестве входных данных 2 кортежа типа E × [E] (псевдо-Хаскеллова запись) и логическое значение (тип C, который является Bool). Как мы видим, он проверяет, является ли голова элементом хвоста. Если это так, он возвращает False и игнорирует рекурсивную часть, в противном случае возвращает рекурсивную часть.

Таким образом, мы можем написать это в Haskell как:

-- types
type A e = [e]
type B e = (e, [e])
type C = Bool

-- functions
p :: A e -> Bool
p [] = True
p (_:_) = False

g :: A e -> (B e, A e)
g (h:t) = ((h, t), t)

c :: C
c = True

plus :: Eq e => B e -> C -> C
plus (h, t) r | elem h t = False
              | otherwise = r

hylo :: Eq e => A e -> C
hylo a | p a = c
       | otherwise = plus b (hylo a')
    where (b, a') = g a

hylo Таким образом, это простая реализация, основанная на определении, где мы, таким образом, берем функции p, c, plus а также g как "строительные блоки".

Другие вопросы по тегам