2016-10-08 2 views
7

Control.Monad.Morph comprendPourquoi Control.Monad.Morph.hoist a-t-il une contrainte Monad?

class MFunctor t where 
    hoist :: Monad m => (forall a. m a -> n a) -> t m b -> t n b 

Pour autant que je sache, aucun des cas inclus utiliser la contrainte Monad m. Comment pourrait-on le faire? Y at-il des instances valides qui utilisent la contrainte (c'est un peu difficile pour moi d'imaginer comment, étant donné que hoist id = id)? Quelle est la signification de la contrainte étant sur m et non n?

+0

Je m'attendais à quelque chose à casser dans ['Control.Monad.Trans.Compose'] (https://hackage.haskell.org/package/mmorph-1.0.6/docs/Control-Monad-Trans-Compose. html), mais tout compile bien sans "Monad m" sur "hoist" ... – Alec

+0

Peut-être parce que cela n'a de sens que pour les monades? C'est un foncteur sur un transformateur monad (pile), autant que je peux voir. – Xeo

+0

@Alec 'Control.Monad.Trans.Compose' n'a pas d'instance' MFunctor'. – Cirdec

Répondre

6

Control.Monad.Morph est un spin-off de pipes, donc je suppose qu'il est là parce que l'instance MFunctor pour Proxy a besoin ... Et bien sûr, il est used there.

instance MFunctor (Proxy a' a b' b) where 
    hoist nat p0 = go (observe p0) 
     where 
     go p = case p of 
      Request a' fa -> Request a' (\a -> go (fa a)) 
      Respond b fb' -> Respond b (\b' -> go (fb' b')) 
      M   m -> M (nat (m >>= \p' -> return (go p'))) 
      Pure r  -> Pure r 

Je ne pense pas qu'il est nécessaire cependant. m >>= return . f est fmap f m. Cela devrait probablement être une contrainte Functor et ce code est antérieur à l'implémentation de la proposition monad-applicative.

+0

Savez-vous ce que ça fait? La contrainte 'Monad' (ou' Functor') est-elle requise pour la sémantique, ou seulement l'efficacité? – dfeuer

+0

C'est mapper 'hoist nat' récursivement dans' m'. Une contrainte 'Functor' ne devrait pas être une exigence surprenante pour tout transformateur' t m a' d'une forme comme 'm (t m a)'. – Cirdec