Could someone please explain to me, why the following code is the memoization:
fib_mem :: Int -> Integer
fib_mem = (map fib [0..] !!)
where fib 0 = 1
fib 1 = 1
fib n = fib_mem (n-2) + fib_mem (n-1)
Could someone please explain to me, why the following code is the memoization:
fib_mem :: Int -> Integer
fib_mem = (map fib [0..] !!)
where fib 0 = 1
fib 1 = 1
fib n = fib_mem (n-2) + fib_mem (n-1)
I assume you're asking how this memoizes fib
. fib
itself is just an ordinary function. The real magic happens in fib_mem = (map fib [0..] !!)
, which memoizes fib
. This expression is equivalent to saying that fib_mem x = (map fib [0..]) !! x
. Let's break this down to see what it's doing:
[0..]
is an infinite list starting [0,1,2,3,..]
and continuing ad infinitum.map fib [0..]
applies fib
to each element of this list, producing a list where each element is the Fibonacci number corresponding to the index of that element, so e.g. 8
is at index 5
. This is the importent step; it memoizes fib
by applying it to every number, so once the value at a particular index is forced, it does not have to be recalculated.!!
is used to get the value back from the list, at the appropriate index.In case you meant "why is it a memoizing function", the answer is, because it is a CAF (constant applicative form) and has a monomorphic type.