2016-03-16 3 views
1

Я пытаюсь изучить трансформаторы монады и есть проблемы, чтобы найти объяснение одной проблемы.MaybeT monad transformer change Writer to WriterT

Скажем, я создаю писатель (в GHCI), как это:

let w = writer (Just "value", ["log"]) :: Writer [String] (Maybe String) 

А теперь я хочу, чтобы обернуть его в MaybeT монады трансформатора. MaybeT конструктор имеет следующий вид:

:t MaybeT 
m (Maybe a) -> MaybeT m a 

и, основываясь на этом, результат вызова MaybeT с w должны иметь тип:

MaybeT (Writer [String]) String 

Но это не делает:

let mt = MaybeT w 
:t mt 
MaybeT (WriterT [String] Data.Functor.Identity.Identity) String 

Мой вопрос в том, почему ghci заменяет Writer [String] на WriterT [String] Identity? Я вообще этого не понимаю, но у меня есть сильное чувство, что я что-то пропустил.

+8

Это то же самое: 'Writer a' является синонимом типа' WriterT a Identity'. – zakyggaps

+3

В старых версиях библиотек вы получили ожидаемый результат. Однако в новых версиях используются монадные трансформаторы «все в порядке», а монады, такие как «Читатель» и «Писатель», определяются с помощью соответствующего трансформатора («Читатель» и «WriterT») и использования монады «Идентичность» (которая «ничего не делает»)). «Читатель» - это просто синоним типа. При объединении этих типов синоним расширяется, и вы видите фактический тип. – Bakuriu

+1

'writer' на самом деле:' writer :: Monad m => (a, w) -> WriterT wma' и 'Writer wa = WriterT w Identity a' - в вашем случае' m = Identity', 'a = Maybe String 'и' w = [String] '- последний аргумент (здесь' a') * curried * в других комментариях и для 'MaybeT' (потому что первый компонент' MaybeT' должен иметь вид '* -> *' ') (PS: * curried * на самом деле не является [правильной концепцией] (https://en.wikipedia.org/wiki/Lambda_calculus#.CE.B7-conversion), но я надеюсь, что вы понимаете, что я говорю) – Carsten

ответ

3

Вот сообщество вики ответ подведения точки замечания:

Это то же самое: Writer a типа синоним WriterT a Identity. Кроме того, writer на самом деле: writer :: Monad m => (a, w) -> WriterT w m a. В вашем случае m = Identity, a = Maybe String и w = [String].