Добавление ограничения в тип результата Monad - PullRequest
3 голосов
/ 10 марта 2020

Я хотел бы создать тип, который является экземпляром Monad, так что тип результата может быть только экземпляром определенного c класса типов. Я хотел бы иметь возможность написать что-то вроде

data T a = T a
class C a where
    ...

instance Monad T where
    return :: (C a) => a -> m a
    return x = ...
    (>>=) :: (C a, C b) => m a -> (a -> m b) -> m b
    p >>= f = ...

В реальном коде, над которым я работаю, мне нужно ограничение класса типов для типа результата, чтобы указанная функция c из класса типов доступно в определениях для return и (>>=). Есть ли способ сделать это?

1 Ответ

1 голос
/ 08 апреля 2020

Согласно комментарию @ chi, лучшим решением, вероятно, является использование либо монад с ограничениями, либо индексированных монад. Оба решения требуют обхода стандартной библиотеки, но это можно сделать с помощью обходных путей, таких как пересвязывание синтаксиса, например, с использованием расширения RebindableSyntax. Наилучшим примером монад с ограничениями, которые мне удалось найти, был пакет constrained-monads , доступный на Hackage, а лучшим примером, с которым мне удалось найти индексированные монады, была запись на Kwang's Haskell. Блог .

...