[Haskell-beginners] EitherT

mike h mike_k_houghton at yahoo.co.uk
Thu Apr 12 20:32:05 UTC 2018


instance Monad m => Functor (EitherT m a) where
   fmap f m = EitherT $ do
       mv <- runEitherT m
       case mv of
           Left  lv -> return $ Left lv
           Right rv -> return $ Right (f rv)


Thanks all :) I think its correct. The compiler does! 
Mike


> On 12 Apr 2018, at 17:27, David McBride <toad3k at gmail.com> wrote:
> 
> You will feel like this was obvious in hindsight.
> 
> fmap :: (a -> b) -> f a -> f b
> fmap (a -> b) -> EitherT m c a -> EitherT m c b
> 
> Now follow the types in your code.
> m :: EitherT m c a
> mv :: Either c a
> return mv :: EitherT m c a -- <- you are back to the wrong type.
> 
> How can you instead return EitherT m c b?
> 
> 
> On Thu, Apr 12, 2018 at 6:25 AM, mike h <mike_k_houghton at yahoo.co.uk <mailto:mike_k_houghton at yahoo.co.uk>> wrote:
> Hi,
> I’m trying to write EitherT from first principles and I’m stuck at the first hurdle - Functor.  I’m looking for a hint rather than a complete answer :)
> 
> 
> This is what I have
> 
> newtype EitherT m a b = EitherT {runEitherT :: m (Either a b)}
> instance Monad m => Functor (EitherT m a) where
>     ---- fmap :: (a -> b) -> f a -> f b
>     fmap f m = EitherT $ do
>         mv <- runEitherT m
>         case mv of
>             Left _   -> return mv
>             Right rv -> return $ Right (f rv)
> 
> 
> 
> and here is the compilers view
> Phrase.hs:31:25: error:
>     • Couldn't match type ‘b’ with ‘a1’
>       ‘b’ is a rigid type variable bound by
>         the type signature for:
>           fmap :: forall a1 b. (a1 -> b) -> EitherT m a a1 -> EitherT m a b
>         at Phrase.hs:27:5-8
>       ‘a1’ is a rigid type variable bound by
>         the type signature for:
>           fmap :: forall a1 b. (a1 -> b) -> EitherT m a a1 -> EitherT m a b
>         at Phrase.hs:27:5-8
>       Expected type: m (Either a a1)
>         Actual type: m (Either a b)
>     • In the expression: return $ Right (f rv)
>       In a case alternative: Right rv -> return $ Right (f rv)
>       In a stmt of a 'do' block:
>         case mv of
>           Left _ -> return mv
>           Right rv -> return $ Right (f rv)
>     • Relevant bindings include
>         rv :: a1 (bound at Phrase.hs:31:19)
>         mv :: Either a a1 (bound at Phrase.hs:28:9)
>         m :: EitherT m a a1 (bound at Phrase.hs:27:12)
>         f :: a1 -> b (bound at Phrase.hs:27:10)
>         fmap :: (a1 -> b) -> EitherT m a a1 -> EitherT m a b
>           (bound at Phrase.hs:27:5)
> 
> 
> what I think I need to do is fmap over the right value after pulling if out of the monad m by doing   mv <- runEitherT m
> 
> these lines from the compiler are particularly confusing
>       Expected type: m (Either a a1)
>         Actual type: m (Either a b)
> 
> as I believe f is    f:: a1->b
> 
> So just hints please and I expect I’ll have another duh moment.
> 
> Thanks
> 
> Mike
> 
> 
> 
> _______________________________________________
> Beginners mailing list
> Beginners at haskell.org <mailto:Beginners at haskell.org>
> http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners <http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners>
> 
> _______________________________________________
> Beginners mailing list
> Beginners at haskell.org
> http://mail.haskell.org/cgi-bin/mailman/listinfo/beginners

-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://mail.haskell.org/pipermail/beginners/attachments/20180412/6d8f6b7d/attachment-0001.html>


More information about the Beginners mailing list