2

I can multiply a list per 2:

(* 2) <$> [1, 2, 3] 

But I want multiply the elements which are Just:

(* 2) <$> [Just 1, Nothing, Just 3] 

Error:

* Non type-variable argument in the constraint: Num (Maybe a) (Use FlexibleContexts to permit this) * When checking the inferred type it :: forall a. (Num (Maybe a), Num a) => [Maybe a] Prelude Data.List 

Another try:

fmap (* 2) [Just 1, Nothing, Just 3] 

Error:

* Non type-variable argument in the constraint: Num (Maybe a) (Use FlexibleContexts to permit this) * When checking the inferred type it :: forall a. (Num (Maybe a), Num a) => [Maybe a] 

I have tried more things: map2, fmap2, map (*2) map, etc.

3 Answers 3

10

A straightforward solution is adding another fmap to get through the Maybe layer:

GHCi> fmap (* 2) <$> [Just 1, Nothing, Just 3] [Just 2,Nothing,Just 6] 

Alternatively, that can be expressed using Compose, which allows handling the two functor layers as one:

GHCi> import Data.Functor.Compose GHCi> (* 2) <$> Compose [Just 1, Nothing, Just 3] Compose [Just 2,Nothing,Just 6] GHCi> getCompose $ (* 2) <$> Compose [Just 1, Nothing, Just 3] [Just 2,Nothing,Just 6] 
Sign up to request clarification or add additional context in comments.

Comments

7

You need to map twice: once to get inside the list, second time to get inside the maybe. The operator <$> only maps once, and you can't use the same operator twice, so you have to add a call to fmap:

fmap (* 2) <$> [Just 1, Nothing, Just 3] 

1 Comment

Sure you can, the syntax is ((* 2) <$>) <$> [Just 1, Nothing, Just 3]. Only do this if you like being deliberately obtuse.
2

You can compose 2 fmap functions:

(fmap . fmap) (*2) [Just 1, Nothing, Just 3] 

The first will be the fmap of the list, the second is the fmap of the maybe.

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.