










Study with the several resources on Docsity
Earn points by helping other students or get them with a premium plan
Prepare for your exams
Study with the several resources on Docsity
Earn points to download
Earn points by helping other students or get them with a premium plan
Recursion in programming, specifically the concept of recursive procedure definitions using the letrec construct. It also covers the concept of recursive functions as fixed points and the fixed-point theorem. Examples and explanations to help understand these concepts.
Typology: Study notes
1 / 18
This page cannot be seen from the preview
Don't miss anything!











Com S 342
Records (to construct linked lists)
Procedure (to implement inductively specified data types)
Mutual depended data structures like classes
Com S 342
Suppose we want to define the operation plus using only the operatorsincrement and decrement.We may write:$
let plus = proc (n, m) if n then (plus dec(n) inc(m)) else
m
in (plus 2 3)
Error reported by apply-envNo binding for plus
Unfortunately this is not a definition, since we are trying to use “plus” beforeit is defined.
Task: Although recursion is fundamental to programming, it is not yetprimitive in the our language, so we must find a way to “program” it!
Com S 342
In general, a fixed point of a function is a value in the function’s domain,which is mapped to itself by the function. Therefore, a fixed point of afunction
is a value
such that
Examples:
(factorial 1) = 1(factorial 2) = 2(fibonacci 0) = 0(fibonacci 1) = 1
However, not all functions have exactly one fixed point: “inc(n) = n + 1” hasnone.
We need to represent the fixed-point operation in our language.
Com S 342
Fixed-point Theorem:
For every
there exists a fixed-point
such that
Proof:
Let
≡ λ
f. (
λ
x. f (x x)) (
λ
x. f (x x))
Now consider:
λ
x. F (x x)) (
λ
x. F (x x))
λ
x. F (x x)) (
λ
x. F (x x)))
Therefore, the “Y combinator” can always be used to find a fixed-point ofan arbitrary lambda expression, if such a fixed-point exists.
Com S 342
The fixed-point operator Y is useless in a call-by-value setting, since theexpression Y g diverges for any g. In call-by-value settings we use,therefore, the operator fix:
fix
≡ λ
f. (
λ
x. f (
λ
y. x x y)) (
λ
x. f (
λ
y. x x y))
Com S 342
m
We can take: plus
fix rplus
plus 1 1
= (fix rplus) 1 1 Æ
(h h) 1 1
where h = (
λ
x. rplus (
λ
y. x x y))
rplus fct 1 1
where fct =
λ
y. h h y
if 1 then (fct 0 2) else 1
fct 0 2
h h 0 2
rplus fct 0 2
if 0 then (fct (pred 0) (succ 2)) else 2
call-by-value
Com S 342
<reclet
<declarations
<declaration
odd
fv(even) and even
fv(odd)
Com S 342
<params /><if
<condition
odd
/>
<arguments <dec <arguments
<else
<proc
<params /><if
<condition
<reference value =
even
/>
<arguments <dec <arguments
<else
Com S 342
… (reclet-exp (decls body)
(let* ((args (eval-rands (get-rands decls) env))
;; filter recursive procedure ids(rec-proc-ids (map car (filter (lambda (p) (procval? (cadr p)))
(zip (get-ids decls) args))))
;; now change closure to closure-rec(new-args (map (lambda (v)
(if (procval? v)
(build-rec-proc v rec-proc-ids)v)) args)))
(eval-expression body (extend-env (get-ids decls) new-args env))))
Com S 342
(define filter
(lambda (p lst)
(if (null? lst)
'() (if (p (car lst))
(cons (car lst) (filter p (cdr lst)))(filter p (cdr lst)))
Com S 342
(app-exp (rator rands)
(let ((proc (eval-expression rator env))
(args (eval-rands rands env)))
(if (procval? proc)
;; add calling-env to resolve occuring recursive procedures
(apply-procval proc args env) (eopl:error 'eval-expression
"Attempt to apply non-procedure ~s" proc))))
Com S 342
(define apply-procval
(lambda (proc args calling-env)
(cases procval proc
(closure (ids body env)
(eval-expression
body(extend-env ids args env)))
(closure-rec (ids body rec-proc-ids env)
(eval-expression
body(extend-env ids args (extend-rec-env rec-proc-ids calling-env env))))