WalzoneInterview Prep
📞 Interviewing soon? Practice with a realistic AI mock phone interview — it calls you, then scores you. First 15 min FREE →

Haskell · Intermediate · question 21 of 100

Can you explain the concept of Functor in Haskell? How is it different from a Monad?

📕 Buy this interview preparation book: 100 Haskell questions & answers — PDF + EPUB for $5

The concept of Functor and Monad are both related to functional programming features in Haskell, and they are both typeclasses representing specific behaviors or properties. However, they have different levels of complexity and functionality. Let’s discuss each one in detail.

## Functor

A ‘Functor‘ is a typeclass representing data types that can be mapped over. In Haskell, a Functor is any type constructor ‘f‘ that has an instance for the ‘Functor‘ typeclass and implements the ‘fmap‘ function. The ‘fmap‘ function has the following type signature:

fmap :: Functor f => (a -> b) -> f a -> f b

Here, ‘f‘ represents a Functor, ‘a‘ and ‘b‘ are types, and the function takes a function of type ‘(a -> b)‘ and a Functor of type ‘f a‘, then applies the function to the contents of the Functor, and returns a new Functor of type ‘f b‘. A common example of a Functor is the ‘Maybe‘ type:

data Maybe a = Nothing | Just a

instance Functor Maybe where
    fmap _ Nothing = Nothing
    fmap f (Just x) = Just (f x)

In this case, the ‘fmap‘ function applies the given function to the value inside the ‘Just‘ constructor, but returns ‘Nothing‘ if the input is ‘Nothing‘.

## Monad

A ‘Monad‘ is a typeclass that represents data types with certain properties that support sequential computation and allow for chaining actions with context. In Haskell, a Monad is any type constructor ‘m‘ that has an instance for the ‘Monad‘ typeclass, and implements the ‘return‘ and ‘>>=‘ (bind) functions. In order to be a Monad, the type must also be a Functor and an instance of the ‘Applicative‘ typeclass.

The ‘return‘ and ‘bind‘ functions have the following type signatures, respectively:

return :: Monad m => a -> m a
(>>=)  :: Monad m => m a -> (a -> m b) -> m b

The ‘return‘ function takes a value of type ‘a‘ and wraps it in a context of type ‘m a‘. The ‘bind‘ function (also written as ‘>>=‘) takes a monadic value ‘m a‘, a function of type ‘(a -> m b)‘, and "binds" the monadic value to this function, resulting in a new monadic value ‘m b‘. This process can be thought of as "chaining" actions together, while preserving the context.

Let’s take a look at the ‘Maybe‘ type as an example of a Monad:

instance Monad Maybe where
    return x = Just x

    (Just x) >>= f = f x
    Nothing  >>= _ = Nothing

The ‘return‘ function simply wraps the input value in the ‘Just‘ constructor, while the ‘bind‘ function unwraps the value from the ‘Just‘ constructor and applies the function to it, or returns ‘Nothing‘ if the input is ‘Nothing‘.

## Functor vs Monad

In summary, Functors and Monads represent different levels of functionality:

1. A Functor is a data type that can be mapped over, containing an implementation of the ‘fmap‘ function, allowing you to apply a function to the contents of the Functor.

2. A Monad is a more powerful abstraction that extends Functor and Applicative. It represents data types that support sequential computation and context preservation, providing the ‘return‘ and ‘bind‘ functions, which allow you to chain actions together and work with values within the monadic context.

To illustrate the difference between ‘fmap‘ (Functor) and ‘bind/>>=‘ (Monad) in a simple way, consider their types:

fmap :: Functor f     => (a ->   b) -> f a -> f b
(>>=) :: Monad m => m a -> (a -> m b) -> m b

The Functor’s ‘fmap‘ takes a regular function ‘(a -> b)‘ and applies it within the functor context. In contrast, the Monad’s ‘bind‘ takes a monadic function ‘(a -> m b)‘ and chains it to a monadic value, allowing you to work with values that have effects or context.

In conclusion, Monad is an extension of Functor, providing more powerful abstractions and functionality. While Functors allow you to map a function over a context, Monads enable you to chain actions together and handle complex scenarios where other actions might depend on previous actions within a context.

Reading is step one. Saying it out loud is the interview. Our AI interviewer calls your phone and runs a realistic Haskell interview — then scores it.
📞 Practice Haskell — free 15 min
📕 Buy this interview preparation book: 100 Haskell questions & answers — PDF + EPUB for $5

All 100 Haskell questions · All topics