Ask Question, Ask an Expert

+61-413 786 465

info@mywordsolution.com

Ask Programming Language Expert

import Data.Array
import Data.IORef (newIORef, readIORef, writeIORef)

You will need to consult the documentation on the imported modules.

Please note: ghci will evaluate expressions, of course, but if the expression is of type (IO a), its value will be *executed* and the resulting value in type a showed.

QUESTION 1

Use imperative-style programming to implement the factorial function in the IO monad. In other words, create and initialize variables (references) using newIORef, modify their values using a while loop with ,readIORef and writeIORef, then have the IO action return a pair consisting of the input (n) and the final result. The expression named mod3 below gives a small example of this kind of programming.

Reading:
- LYAH Chapter 9 "Input and Output" up to the first occurrence of "Control.Monad".
- Module documentation for the functions imported from Data.IORef (see the top of this file).

-}

while :: IO Bool -> IO () -> IO ()
while test body =
do b <- test
if b
then do {body ; while test body} -- same-line syntax for do
else return ()

-- remainder when integer-dividing n by 3
mod3 :: Integer -> IO Integer
mod3 n = do r <- newIORef n
while
(do {v <- readIORef r; return (v >= 3)})
(do {v <- readIORef r; writeIORef r (v-3)})
readIORef r

-- ghci> fact 4
-- 24
fact :: Integer -> IO (Integer, Integer)
fact n =
do
undefined

{- CODE FOR QUESTIONS 2 AND 3

Below we give a roll-your-own alternative to Data.IORef. We model memory as an array and memory locations (references) as indices into the array. Using this model it is straightforward to implement creation, reading and writing of references.

However, as with the IO monad, we use a layer of abstraction to hide all the details of memory management. Instead of (IO a), we will have (MM a) -- "MM" for "memory modifiers".

The implementation of actions in (IO a) is completely hidden from us in Haskell. The actions in (MM a) will all be constructed from scratch using the usual kinds of Haskell data. The basic decision in designing MM is how represent actions.

Since we're focusing on references, it's natural to consider an action as something, that in addition to producing a value, modifies memory.

Modifying something in a functional setting is done by applying a function which produces the new "modified" copy. Thus an action can be thought of as a function that takes a memory (array), and from it produces both a value and a new memory (an array with possibly some values updated).

More formally, actions in (MM a) are elements of the type

Mem -> (Mem,a)

so we define

data MM a = MM (Mem -> (Mem, a))

We want to use the same "do" syntax to hide memory management details that IO does. Fortunately, it turns out that MM is a monad.

The definition of (>>=) for MM is not immediately transparent, but it need not be to do Question 2. For question 2, MM can be thought of as replacement for IO and programs using "do" can be constructed analogously. Question 3 requires understanding details of the construction of MM and its operations.

-}

-- for convenience
type Z = Integer

-- raise an error if an attempt to index the array is out of bounds
checkBounds :: String -> Z -> Array Z a -> ()
checkBounds msg i a =
let (lower, upper) = bounds a
in if i >= lower && i < upper
then ()
else error msg

-- Memory is modeled by (Mem n i a) where:
-- - n is the size of the memory (number of locations)
-- - a is an array, with indexes 0<=i-- values stored in memory and
-- - i is the next position to allocate at
data Mem = Mem Z Z (Array Z Z)
deriving Show

-- A reference is an index into the memory array.
type Ref = Z

-- Memory-modifying computations with result type a.
data MM a = MM (Mem -> (Mem, a))

-- ignore, not needed for either question!
instance Functor MM where
fmap f (MM g) = MM (\m -> let (m',v) = g m in (m', f v))

-- ignore, not needed for either question!
instance Applicative MM where
pure x = MM (\m -> (m,x))
MM f <*> MM g =
MM (\m-> let (m', f') = f m
(m'', x) = g m'
in (m'', f' x))

instance Monad MM where

-- action that produces x without modifying memory
return x = MM (\m -> (m,x))

-- like composing f and g, except memory modifications are chained
(MM a) >>= f =
MM (\m-> let (m', v) = a m
MM b = f v
in b m')

-- create an initial memory of size n
initMem :: Z -> Mem
initMem n = Mem n 0 (array (0,n) [])

-- return a new reference, initialized to v
newRef :: Z -> MM Ref
newRef v =
MM f where
f (Mem n i a) = (m', i )
where m' = Mem n (i+1) a'
a' = a // [(i,v)]

writeRef :: Ref -> Z -> MM ()
writeRef j v =
MM f where f (Mem n i a) = (Mem n i a', ())
where a' = a // [(j,v)]

readRef :: Ref -> MM Z
readRef j =
MM f where f m@(Mem _ _ a) = (m, a!j)

run :: Z -> MM a -> a
run n (MM mm) =
snd $ mm (initMem n)

-- run the action and return a list of memory contents
runDump :: Z -> MM a -> [Z]
runDump n (MM mm) =
elems a where
Mem _ _ a = fst $ mm (initMem n)

-- The test needs to be in MM Bool instead of just Bool because it
-- will generally need to refer to values stored in memory.
while' :: MM Bool -> MM () -> MM ()
while' test body =
do b <- test
if b
then do {body ; while' test body}
else return ()

{- QUESTION 2

Repeat Question 1, but using MM and its reference operations in place of IO, and while' in place of while. You can execute elements of (MM a) using the run function above (which also takes an argument for the size of memory to use).

ghci> run 10 (fact' 4)
24

-}

fact' :: Integer -> MM (Integer, Integer)
fact' n =
do undefined

{- QUESTION 3 -- EXTRA CREDIT

Implement versions of newRef, writeRef and readRef that, instead of returning a single reference, allocate a pair of consecutive storage locations and return the first address (index). Effectively, the operations deal with 2-cell objects. The advantage of this is that linked structures, like linked lists, can be implemented.

Below is given the types for the new operations, and a program appendTest that creates two linked lists then appends them by changing the pointer at the end of the first list. The example uses some auxiliary functions. You just need to implement the three reference operations.

-}

newRef2 :: Z -> Z -> MM Ref
newRef2 u v =
undefined

writeRef2 :: Ref -> Z -> Z -> MM ()
writeRef2 j u v =
undefined

readRef2 :: Ref -> MM (Z,Z)
readRef2 j =
undefined

mkList :: [Z] -> MM Ref
-- Use -1 for "nil", i.e. null pointer
mkList [] = return (-1)
mkList (x:xs) =
do tail <- mkList xs
head <- newRef2 x tail
return head

append :: Ref -> Ref -> MM (Ref)
-- x and y must be pointers to lists
append (-1) y = return y
append x y =
do append' x
return x
where append' x =
do (v,i) <- readRef2 x
if i == -1
then writeRef2 x v y
else append' i

collectList :: Ref -> MM [Z]
collectList (-1) = return []
collectList i =
do (x,j) <- readRef2 i
xs <- collectList j
return (x:xs)

-- ghci> run 37 appendTest
-- [1,2,3,4,5,6]
appendTest :: MM [Z]
appendTest =
do l <- mkList [1,2,3]
newRef 17 >> newRef 17 >> newRef 17 -- some irrelevant creations
l' <- mkList [4,5,6]
newRef 17 >> newRef 17 >> newRef 17 -- ditto
x <- append l l'
result <- collectList x
return result

Programming Language, Programming

  • Category:- Programming Language
  • Reference No.:- M91424410
  • Price:- $80

Guranteed 48 Hours Delivery, In Price:- $80

Have any Question?


Related Questions in Programming Language

Question 1 what is a computer program what is structured

Question: 1. What is a Computer program? What is structured programming? 2. What is modular programming? Why we use it? 3. Please evaluate Sin (x) by infinite series. Then write an algorithm to implement it with up to th ...

Task working with arraysoverviewin this task you will

Task: Working with Arrays Overview In this task you will create a simple program which will create and work with an array of strings. This array will then be populated with values, printed out to the console, and then, w ...

Task arrays and structsoverviewin this task you will

Task: Arrays and Structs Overview In this task you will continue to work on the knight database to help Camelot keep track of all of their knights. We can now add a kingdom struct to help work with and manage all of the ...

Overviewthis tasks provides you an opportunity to get

Overview This tasks provides you an opportunity to get feedback on your Learning Summary Report. The Learning Summary Report outlines how the work you have completed demonstrates that you have met all of the unit's learn ...

Assignment - haskell program for regular expression

Assignment - Haskell Program for Regular Expression Matching Your assignment is to modify the slowgrep.hs Haskell program presented in class and the online notes, according to the instructions below. You may carry out th ...

Assignment task -q1 a the fibonacci numbers are the numbers

Assignment Task - Q1. (a) The Fibonacci numbers are the numbers in the following integer sequence, called the Fibonacci sequence, and are characterised by the fact that every number after the first two is the sum of the ...

Question - create a microsoft word macro using vba visual

Question - Create a Microsoft Word macro using VBA (Visual Basic for Applications). Name the macro "highlight." The macro should highlight every third line of text in a document. (Imagine creating highlighting that will ...

Assignmentquestion onegiving the following code snippet

Assignment Question One Giving the following code snippet. What kind of errors you will get and how can you correct it. A. public class HelloJava { public static void main(String args[]) { int x=10; int y=2; System.out.p ...

Assignment - proposal literature review research method1

Assignment - Proposal, Literature Review, Research Method 1. Abstract - Summary of the knowledge gap: problems of the existing research - Aim of the research, summary of what this project is to achieve - Summary of the a ...

Extend the adworks applicationi add dialogs to allow the

Extend the AdWorks application I. Add Dialogs to allow the user to Add, Edit, Read and Delete a Customer and refresh the view accordingly. 1. The user should be able to select a specific customer from the DataGrid and cl ...

  • 4,153,160 Questions Asked
  • 13,132 Experts
  • 2,558,936 Questions Answered

Ask Experts for help!!

Looking for Assignment Help?

Start excelling in your Courses, Get help with Assignment

Write us your full requirement for evaluation and you will receive response within 20 minutes turnaround time.

Ask Now Help with Problems, Get a Best Answer

Why might a bank avoid the use of interest rate swaps even

Why might a bank avoid the use of interest rate swaps, even when the institution is exposed to significant interest rate

Describe the difference between zero coupon bonds and

Describe the difference between zero coupon bonds and coupon bonds. Under what conditions will a coupon bond sell at a p

Compute the present value of an annuity of 880 per year

Compute the present value of an annuity of $ 880 per year for 16 years, given a discount rate of 6 percent per annum. As

Compute the present value of an 1150 payment made in ten

Compute the present value of an $1,150 payment made in ten years when the discount rate is 12 percent. (Do not round int

Compute the present value of an annuity of 699 per year

Compute the present value of an annuity of $ 699 per year for 19 years, given a discount rate of 6 percent per annum. As