Search code examples
haskellnewtype

Newtype with Tuple


About this code from LearnYouaHaskell:

newtype Pair b a = Pair {getPair :: (a,b)}
instance Functor (Pair c) where
  fmap f (Pair (x, y)) = Pair (f x, y)

I understand that the first line creates a new data type from tuple. However, why does the order of arguments switched from Pair b a to getPair :: (a,b)? If I switch one of the order, then I get an error due to pattern matching in the definition of fmap.


Solution

  • The Functor class requires a single type argument, while the Pair type has two. The instance definition for Pair:

    instance Functor (Pair c) where ...
    

    fixes the first type argument, which corresponds to the second element of the tuple. This means that fmap transforms the first element of the tuple. If the type arguments for Pair were in the other order, you would transform the second tuple element instead and the definition would have to change to:

    fmap f (Pair (x, y)) = Pair (x, f y)
    

    note the built-in definition for Functor on pairs already behaves this way e.g.

    import Data.Functor
    fmap (+1) ("first", 3)