The goal for this assignment is to get more comfortable with using custom data types, functors, applicative functors, and monads.
All your code for this assignment should go into a file named "MP3.hs" within
the "src/mps
" subdirectory in your repository.
Given the type declaration:
data Expr = Val Int | Add Expr Expr
define a higher-order function:
folde :: (Int -> a) -> (a -> a -> a) -> Expr -> a
such that folde f g
replaces each Val
constructor in an expression by
the function f
, and each Add
constructor by the function g
.
Using folde
, define a function "eval :: Expr -> Int
" that evaluates an
expression to an integer value, and a function "size :: Expr -> Int
" that
calculates the number of values in an expression.
An alternative way to make a list into an applicative functor is to have
pure
create an infinite list of copies of its argument, and the <*>
operator apply each argument function to the corresponding argument value at
the same position.
Because functor and applicative instances already exist for the list, a
common strategy is to define a "wrapper" type for which we can then proceed
to define instances. ZipList
, below, is such a wrapper type. Complete the
following declarations to implement the idea described above:
data ZipList a = Z [a] deriving Show
instance Functor ZipList where
-- fmap :: (a -> b) -> ZipList a -> ZipList b
fmap g (Z xs) = ...
instance Applicative ZipList where
-- pure :: a -> ZipList a
pure x = ...
-- <*> :: ZipList (a -> b) -> ZipList a -> ZipList b
(Z gs) <*> (Z xs) = ...
Relying on the State
monad defined in class, define the "enqueue :: a ->
State [a] ()
" and "dequeue :: State [a] a
" functions that provide queue
semantics (as we did with the pop
and push
functions in class). Provide
an example in a do
block that demonstrates how these functions could be
used to manipulate and use values stored on a queue within the state monad.
Given the following type of expressions:
data Expr a = Var a | Val Int | Add (Expr a) (Expr a) deriving Show
that contain variables of some type a
, show how to make this type into
instances of the Functor
, Applicative
, and Monad
classes. With the aid
of an example, explain what the >>=
operator for this type does.